add sborka

This commit is contained in:
2026-03-31 10:27:04 +03:00
commit f5e5f56c84
2345 changed files with 382127 additions and 0 deletions

View File

@@ -0,0 +1,360 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "AEK-971"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "4Assault Rifle"
SWEP.Description = "Experimental assault rifle using a unique dampening mechanism to reduce felt recoil. High fire rate but medicore range."
SWEP.Description_Quote = "Saw extensive use in the Battle for Paris." -- Battlefield 3 (2011)
SWEP.Trivia_Caliber = "5.45x39mm"
SWEP.Trivia_Manufacturer = "Kovrovskiy Mekhanicheskiy Zavod"
SWEP.Trivia_Year = "1990"
SWEP.Faction = TacRP.FACTION_MILITIA
SWEP.Credits = [[
Assets: Casper, arby26
Animation: Tactical Intervention]]
SWEP.ViewModel = "models/weapons/tacint_shark/v_aek.mdl"
SWEP.WorldModel = "models/weapons/tacint_shark/w_aek.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 16,
Damage_Min = 11,
Range_Min = 400,
Range_Max = 2000,
RPM = 900,
RecoilSpreadPenalty = 0.0025,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 8,
Damage_Min = 4,
},
[TacRP.BALANCE_OLDSCHOOL] = {
HipFireSpreadPenalty = 0.012,
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 20
SWEP.Damage_Min = 12
SWEP.Range_Min = 400 // distance for which to maintain maximum damage
SWEP.Range_Max = 2400 // distance at which we drop to minimum damage
SWEP.Penetration = 7 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.725
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.85,
[HITGROUP_RIGHTLEG] = 0.85,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 25000
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 900
SWEP.Spread = 0.006
SWEP.ShootTimeMult = 0.65
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 9
SWEP.RecoilResetTime = 0.01
SWEP.RecoilDissipationRate = 35
SWEP.RecoilFirstShotMult = 1.5
SWEP.RecoilVisualKick = 0.4
SWEP.RecoilKick = 4
SWEP.RecoilStability = 0.5
SWEP.RecoilAltMultiplier = 300
SWEP.RecoilSpreadPenalty = 0.0019
SWEP.HipFireSpreadPenalty = 0.04
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.92
SWEP.ShootingSpeedMult = 0.8
SWEP.SightedSpeedMult = 0.6
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.33
SWEP.SprintToFireTime = 0.37
SWEP.Sway = 1.25
SWEP.ScopedSway = 0.15
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2.5, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(-0.05, 1.35, -0.5)
SWEP.SightPos = Vector(-4.7, -7.5, -4)
SWEP.CorrectivePos = Vector(-0.02, 0, -0.05)
SWEP.CorrectiveAng = Angle(0.75, 0.7, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, -2, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint_shark/magazines/aek.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.65
SWEP.DropMagazineTime = 0.65
SWEP.FreeAimMaxAngle = 4.5
// sounds
local path = "tacint_shark/weapons/aek971/ak47"
SWEP.Sound_Shoot = "^" .. path .. "_shoot.wav"
SWEP.Sound_Shoot_Silenced = "tacint_shark/weapons/an94/ak47_suppressed_fire1.wav"
SWEP.Vol_Shoot = 120
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "deploy",
["fire_iron"] = "fire1_M",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_R"},
["melee"] = {"melee1", "melee2"},
["jam"] = "mid_reload"
}
// attachments
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
}
},
["tactical"] = {
BGs_VM = {
{2, 1}
},
},
["akmount"] = {
BGs_VM = {
{2, 0}
},
AttPosMods = {
[1] = {
Pos_VM = Vector(-5.5, 0.4, 1.5),
Pos_WM = Vector(-0.4, 2, 0.5),
VMScale = 1.2,
}
},
SortOrder = 2,
},
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.65, -0.5),
vm_ang = Angle(0, 1, 0),
t = 0.15,
tmax = 0.15,
bones = {
{
bone = "ValveBiped.bolt",
pos = Vector(0, 0, -3),
t0 = 0.02,
t1 = 0.1,
},
},
}
SWEP.NoRMR = true
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium", "optic_sniper", "optic_ak"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
InstalledElements = {"tactical"},
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.75,
Pos_VM = Vector(-5.8, 0.2, 4),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 3, 0.6),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = {"silencer", "muzz_ak"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
VMScale = 0.9,
WMScale = 0.9,
Pos_VM = Vector(-3.5, 0.075, 26.25),
Pos_WM = Vector(-.15, 24.5, -1.5),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
Pos_VM = Vector(-4.5, -0.1, 19),
Pos_WM = Vector(0.2, 16, -0.5),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, -90, -90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock", "acc_sling", "acc_duffle", "perk_extendedmag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_aek.remove_clip", path .. "_clipout.wav")
addsound("tacint_aek.insert_clip", path .. "_clipin.wav")
addsound("tacint_aek.boltaction", path .. "_boltpull.wav")
addsound("tacint_aek.Buttstock_Back", "tacrp/weapons/ak47/ak47_buttstock_back.wav")

View File

@@ -0,0 +1,361 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "AK-12"
SWEP.AbbrevName = "AK-12"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "1Elite"
SWEP.SubCatType = "4Assault Rifle"
SWEP.Description = "One of many attempts at modernizing the AK, this experimental model uses burst fire and allows for quick swapping of the weapon's caliber."
SWEP.Description_Quote = "Found on a dead Spetsnaz soldier." -- Killing Floor 2, explaining where the weapon came from.
SWEP.Trivia_Caliber = "5.45x39mm"
SWEP.Trivia_Manufacturer = "Kalashnikov Concern"
SWEP.Trivia_Year = "2012"
SWEP.Faction = TacRP.FACTION_MILITIA
SWEP.Credits = [[
Assets: Counter Strike: Online 2
Animation: Tactical Intervention]]
SWEP.ViewModel = "models/weapons/tacint_extras/v_ak12.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_ak12.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 24,
Damage_Min = 16,
RecoilKick = 2,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 15,
Damage_Min = 12,
Range_Min = 600,
Range_Max = 2500,
RecoilSpreadPenalty = 0.0025,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 12,
Damage_Min = 6,
RecoilSpreadPenalty = 0.0011,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilMaximum = 18,
RecoilDissipationRate = 15,
RecoilSpreadPenalty = 0.004
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 28
SWEP.Damage_Min = 16
SWEP.Range_Min = 1200
SWEP.Range_Max = 3200
SWEP.Penetration = 6 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.7
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.85,
[HITGROUP_RIGHTLEG] = 0.85,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 25000
// misc. shooting
SWEP.Firemodes = {
-3,
2,
1
}
SWEP.PostBurstDelay = 0.08
SWEP.RPM = 700
SWEP.RPMMultBurst = 800 / 700
SWEP.Spread = 0.004
SWEP.ShootTimeMult = 0.6
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 10
SWEP.RecoilResetTime = 0.01
SWEP.RecoilDissipationRate = 36
SWEP.RecoilFirstShotMult = 1
SWEP.RecoilVisualKick = 1
SWEP.RecoilKick = 2
SWEP.RecoilStability = 0.55
SWEP.RecoilSpreadPenalty = 0.0026
SWEP.HipFireSpreadPenalty = 0.03
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.925
SWEP.ShootingSpeedMult = 0.85
SWEP.SightedSpeedMult = 0.65
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.37
SWEP.SprintToFireTime = 0.4
SWEP.Sway = 1.25
SWEP.ScopedSway = 0.15
// hold types
SWEP.HoldType = "smg"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -3, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(-0.25, 0, -1)
SWEP.SightPos = Vector(-4.48, -7, -3.55)
SWEP.CorrectivePos = Vector(0.03, 0, 0.06)
SWEP.CorrectiveAng = Angle(0.64, 0.1, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, -2, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 0.95
SWEP.DropMagazineModel = "models/weapons/tacint_shark/magazines/aek.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.35
SWEP.DropMagazineTime = 0.45
SWEP.FreeAimMaxAngle = 4
// sounds
local path = "tacrp/weapons/ak47/ak47_"
local path1 = "tacint_extras/ak12/"
SWEP.Sound_Shoot = "^" .. path1 .. "ak12-1.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 120
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "deploy",
["fire_iron"] = "fire1_M",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = "fire3_M",
["fire5"] = "fire3_M",
["melee"] = {"melee1", "melee2"},
["jam"] = "midreload"
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.1, -0.1),
vm_ang = Angle(0, 0.1, 0),
t = 0.15,
tmax = 0.15,
bones = {
{
bone = "ValveBiped.bolt_cover",
pos = Vector(0, 0, -3),
t0 = 0.02,
t1 = 0.12,
},
},
}
// attachments
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
}
},
["sight"] = {
BGs_VM = {
{2, 1}
},
},
}
SWEP.NoRMR = true
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium", "optic_sniper"},
Bone = "ValveBiped._ROOT_AMD65",
WMBone = "Box01",
InstalledElements = {"sight"},
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
VMScale = 0.9,
Pos_VM = Vector(-4.55, 0.225, 3.5),
Pos_WM = Vector(0, 4, 0.5),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped._ROOT_AMD65",
WMBone = "Box01",
VMScale = 0.9,
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
Pos_VM = Vector(-2.4, 0.25, 30),
Pos_WM = Vector(0, 27.5, -1.5),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped._ROOT_AMD65",
WMBone = "Box01",
InstalledElements = {"tactical"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
Pos_VM = Vector(-2.5, -0.5, 15.5),
Pos_WM = Vector(0.65, 14, -1.5),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, -90, -90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock", "acc_sling", "acc_duffle", "perk_extendedmag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_4pos"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle", "ammo_ak12"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_ak12.remove_clip", "TacRP/weapons/ak47/ak47_remove_clip.wav")
addsound("tacint_ak12.insert_clip", "TacRP/weapons/ak47/ak47_insert_clip.wav")
addsound("tacint_ak12.Bolt_Back", path1 .. "ak12_reload.wav")
addsound("tacint_ak12.Bolt_Release", "common/null.wav")
addsound("tacint_ak12.Rifle_catch", path .. "rifle_catch.wav")
addsound("tacint_ak12.Buttstock_Lockback", path1 .. "ak12_draw.wav")

View File

@@ -0,0 +1,377 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "AK-74"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "3Security"
SWEP.SubCatType = "4Assault Rifle"
SWEP.Description = "A well-rounded staple from Eastern Europe with controllable recoil and good range. Modifications include lightweight furniture and mounts for dovetail optics."
SWEP.Description_Quote = "\"On the battlefield, it's probably better to wound a man than to kill him.\"" -- 'The History of the AK-74' by S1apSh0es - https://youtu.be/6jZOzB3oeSs?feature=shared
SWEP.Trivia_Caliber = "5.45x39mm"
SWEP.Trivia_Manufacturer = "Kalashnikov Concern"
SWEP.Trivia_Year = "1974"
SWEP.Faction = TacRP.FACTION_MILITIA
SWEP.Credits = [[
Model: Twinke Masta, TheLama
Texture: Millenia, The Spork
Sound: Vunsunta
Animation: Tactical Intervention]]
SWEP.ViewModel = "models/weapons/tacint_extras/v_ak74.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_ak74.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 23,
Damage_Min = 15,
RecoilKick = 2.5,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 16,
Damage_Min = 11,
Range_Min = 400,
Range_Max = 2500,
RPM = 600,
RecoilSpreadPenalty = 0.0025,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 8,
Damage_Min = 4,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilMaximum = 20,
RecoilSpreadPenalty = 0.003,
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 22
SWEP.Damage_Min = 12
SWEP.Range_Min = 1000
SWEP.Range_Max = 2700
SWEP.Penetration = 7 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.7
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.85,
[HITGROUP_RIGHTLEG] = 0.85,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 21000
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 650
SWEP.Spread = 0.004
SWEP.ShootTimeMult = 0.5
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 10
SWEP.RecoilResetTime = 0
SWEP.RecoilDissipationRate = 36
SWEP.RecoilFirstShotMult = 1
SWEP.RecoilVisualKick = 1
SWEP.RecoilKick = 3
SWEP.RecoilStability = 0.35
SWEP.RecoilAltMultiplier = 150
SWEP.RecoilSpreadPenalty = 0.002
SWEP.HipFireSpreadPenalty = 0.05
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.9
SWEP.ShootingSpeedMult = 0.75
SWEP.SightedSpeedMult = 0.6
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.4
SWEP.SprintToFireTime = 0.4
SWEP.Sway = 1.25
SWEP.ScopedSway = 0.15
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -4)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0.02, -0.5, 0)
SWEP.SightPos = Vector(-4.66, -7.5, -3)
SWEP.CorrectivePos = Vector(0, 0, -0.05)
SWEP.CorrectiveAng = Angle(0.75, 0.7, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, -2, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint_shark/magazines/74u.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.65
SWEP.DropMagazineTime = 0.65
SWEP.FreeAimMaxAngle = 5
// sounds
local path = "tacrp/weapons/ak47/ak47_"
local path1 = "tacint_shark/weapons/ak74u/"
local path2 = "tacint_extras/ak74/"
SWEP.Sound_Shoot = "^" .. path2 .. "ak47-1.wav"
SWEP.Sound_Shoot_Silenced = path2 .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 120
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "unholster",
["fire_iron"] = "fire1_M",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"},
["jam"] = "mid_reload",
}
SWEP.DeployTimeMult = 2.25
// attachments
SWEP.AttachmentElements = {
["polymer"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
}
},
["tactical"] = {
BGs_VM = {
{2, 1}
},
BGs_WM = {
{2, 1}
},
},
["akmount"] = {
BGs_VM = {
{2, 0}
},
BGs_WM = {
{2, 0}
},
AttPosMods = {
[1] = {
Pos_VM = Vector(-5.5, 0.5, 2),
Pos_WM = Vector(-0.4, 1, 0.5),
}
},
SortOrder = 2,
},
}
SWEP.NoRMR = true
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.4, -0.3),
vm_ang = Angle(0, 0.5, 0),
t = 0.2,
tmax = 0.2,
bones = {
{
bone = "ValveBiped.bolt",
pos = Vector(0, 0, -3),
t0 = 0.01,
t1 = 0.15,
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium", "optic_sniper", "optic_ak"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
InstalledElements = {"tactical"},
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.75,
WMScale = 0.75,
Pos_VM = Vector(-5.5, 0.15, 2.4),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 0.4, 0.1),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = {"silencer", "muzz_ak"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
VMScale = 0.8,
WMScale = 0.8,
Pos_VM = Vector(-3.3, 0.14, 29),
Pos_WM = Vector(0, 27.4, -2),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
Pos_VM = Vector(-3.25, -0.1, 19),
Pos_WM = Vector(0, 19, -2.5),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, -90, 180),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_ak74", "acc_sling", "acc_duffle", "perk_extendedmag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_extras_ak74.remove_clip", path1 .. "clipout.wav")
addsound("tacint_extras_ak74.insert_clip", path1 .. "clipin.wav")
addsound("tacint_extras_ak74.boltaction", path .. "boltaction.wav")
addsound("tacint_extras_ak74.Buttstock_Back", path .. "buttstock_back.wav")

View File

@@ -0,0 +1,365 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "АКС-74У"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "3Security"
SWEP.SubCatType = "3Submachine Gun"
SWEP.Description = "SMG-sized carbine designed for tank crews and special forces. Impressive firepower in a small package, but not gentle in terms of recoil."
SWEP.Description_Quote = "\"Mother Russia can rot, for all I care.\""
SWEP.Trivia_Caliber = "5.45x39mm"
SWEP.Trivia_Manufacturer = "Tula Arms Plant"
SWEP.Trivia_Year = "1979"
SWEP.Faction = TacRP.FACTION_MILITIA
SWEP.Credits = [[
Model: TheLama; Compile: Bushmasta101
Texture: Thanez
Sound: BlitzBoaR/CC5/modderfreak, .exe
Animation: Tactical Intervention]]
SWEP.ViewModel = "models/weapons/tacint_shark/v_74u.mdl"
SWEP.WorldModel = "models/weapons/tacint_shark/w_74u.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 25,
Damage_Min = 13,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 14,
Damage_Min = 7,
Range_Min = 600,
Range_Max = 1800,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 10,
Damage_Min = 4,
RecoilSpreadPenalty = 0.0022,
},
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 23
SWEP.Damage_Min = 10
SWEP.Range_Min = 500
SWEP.Range_Max = 1900
SWEP.Penetration = 7 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.725
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.85,
[HITGROUP_RIGHTLEG] = 0.85,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 18000
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 700
SWEP.Spread = 0.01
SWEP.ShootTimeMult = 0.5
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 7
SWEP.RecoilResetTime = 0.01
SWEP.RecoilDissipationRate = 32
SWEP.RecoilFirstShotMult = 1.25
SWEP.RecoilVisualKick = 1
SWEP.RecoilKick = 4
SWEP.RecoilStability = 0.4
SWEP.RecoilAltMultiplier = 300
SWEP.RecoilSpreadPenalty = 0.0031
SWEP.HipFireSpreadPenalty = 0.022
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.925
SWEP.ShootingSpeedMult = 0.8
SWEP.SightedSpeedMult = 0.7
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.3
SWEP.SprintToFireTime = 0.33
SWEP.Sway = 0.9
SWEP.ScopedSway = 0.2
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -4)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0.05, -0.5, -0.5)
SWEP.SightPos = Vector(-4.66, -7.5, -2.8)
SWEP.CorrectivePos = Vector(0, 0, -0.05)
SWEP.CorrectiveAng = Angle(0.8, 0.7, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, -2, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
SWEP.DeployTimeMult = 0.9
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 0.925
SWEP.DropMagazineModel = "models/weapons/tacint_shark/magazines/74u.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.65
SWEP.DropMagazineTime = 0.65
SWEP.FreeAimMaxAngle = 3.5
// sounds
local path = "tacrp/weapons/ak47/ak47_"
local path1 = "tacint_shark/weapons/ak74u/"
SWEP.Sound_Shoot = "^" .. path1 .. "ak47-1.wav"
SWEP.Sound_Shoot_Silenced = path1 .. "g3sg1-1.wav"
SWEP.Pitch_Shoot = 100
SWEP.Vol_Shoot = 120
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "deploy",
["fire_iron"] = "fire1_M",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"},
["jam"] = "mid_reload"
}
// attachments
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
}
},
["tactical"] = {
BGs_VM = {
{2, 1}
},
BGs_WM = {
{2, 1}
},
},
["akmount"] = {
BGs_VM = {
{2, 0}
},
BGs_WM = {
{2, 0}
},
AttPosMods = {
[1] = {
Pos_VM = Vector(-5, 0.475, 1.5),
Pos_WM = Vector(-0.1, -1, 0.5),
VMScale = 1.2,
}
},
SortOrder = 2,
},
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.4, -0.2),
vm_ang = Angle(0, 0.5, 0),
t = 0.2,
tmax = 0.2,
bones = {
{
bone = "ValveBiped.bolt",
pos = Vector(0, 0, -3),
t0 = 0.01,
t1 = 0.15,
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium", "optic_sniper", "optic_ak"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
InstalledElements = {"tactical"},
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.75,
Pos_VM = Vector(-5.8, 0.25, 3),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0.05, 2.5, 1.2),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = {"silencer", "muzz_ak"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
VMScale = 0.75,
WMScale = 0.85,
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
Pos_VM = Vector(-3.35, 0.14, 19.3),
Pos_WM = Vector(0, 18.5, -1.65),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
Pos_VM = Vector(-4.25, 0.6, 12),
Pos_WM = Vector(-0.4, 10, -0.5),
Ang_VM = Angle(90, 0, 75),
Ang_WM = Angle(0, -90, 75),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock", "acc_sling", "acc_duffle", "perk_extendedmag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_74u.remove_clip", path1 .. "clipout.wav")
addsound("tacint_74u.insert_clip", path1 .. "clipin.wav")
addsound("tacint_74u.boltaction", path .. "boltaction.wav")
addsound("tacint_74u.Buttstock_Back", path .. "buttstock_back.wav")

View File

@@ -0,0 +1,367 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "АН-94"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "1Elite"
SWEP.SubCatType = "4Assault Rifle"
SWEP.Description = "Experimental assault rifle with a unique 2-round \"hyperburst.\" The rifle's complex mechanism affords low recoil but is very bulky."
SWEP.Description_Quote = "\"Antje\""
SWEP.Trivia_Caliber = "5.45x39mm"
SWEP.Trivia_Manufacturer = "Kalashnikov Concern"
SWEP.Trivia_Year = "1994"
SWEP.Faction = TacRP.FACTION_NEUTRAL
SWEP.Credits = [[
Assets: Firearms: Source
Animation: Tactical Intervention]]
SWEP.ViewModel = "models/weapons/tacint_shark/v_an94.mdl"
SWEP.WorldModel = "models/weapons/tacint_shark/w_an94.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 23,
Damage_Min = 15,
RecoilKick = 3,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 16,
Damage_Min = 11,
Range_Min = 400,
Range_Max = 2000,
RecoilSpreadPenalty = 0.0025,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 8,
Damage_Min = 4,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilResetTime = 0.3,
RecoilSpreadPenalty = 0.004
},
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 24
SWEP.Damage_Min = 17
SWEP.Range_Min = 1100
SWEP.Range_Max = 3300
SWEP.Penetration = 7 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.725
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.85,
[HITGROUP_RIGHTLEG] = 0.85,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 25000
// misc. shooting
SWEP.Firemodes = {
-2,
2,
1
}
SWEP.RPM = 600
SWEP.RPMMultBurst = 3
SWEP.PostBurstDelay = 0.25
SWEP.RunawayBurst = true
SWEP.Spread = 0.006
SWEP.ShootTimeMult = 0.5
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 4
SWEP.RecoilResetTime = 0.12
SWEP.RecoilDissipationRate = 10
SWEP.RecoilFirstShotMult = 0.35 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 1
SWEP.RecoilKick = 2
SWEP.RecoilStability = 0.5
SWEP.RecoilAltMultiplier = 55
SWEP.RecoilSpreadPenalty = 0.006
SWEP.HipFireSpreadPenalty = 0.035
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.8
SWEP.ShootingSpeedMult = 0.75
SWEP.SightedSpeedMult = 0.5
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.42
SWEP.SprintToFireTime = 0.45
SWEP.Sway = 1.3
SWEP.ScopedSway = 0.2
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -3, -4)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(-0.03, -0.15, 0)
SWEP.SightPos = Vector(-4.66, -7.5, -2.45)
SWEP.CorrectivePos = Vector(0, 0, -0.05)
SWEP.CorrectiveAng = Angle(0.75, 0.7, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, -2, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1.05
SWEP.DropMagazineModel = "models/weapons/tacint_shark/magazines/aek.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.65
SWEP.DropMagazineTime = 0.65
SWEP.FreeAimMaxAngle = 4.5
// sounds
local path = "tacint_shark/weapons/an94/ak47_"
SWEP.Sound_Shoot = "tacint_shark/weapons/an94/an-94_fire.wav"
SWEP.Sound_Shoot_Silenced = path .. "suppressed_fire1.wav"
SWEP.Vol_Shoot = 120
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "deploy",
["fire_iron"] = "fire1_M",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"},
["jam"] = "mid_reload"
}
// attachments
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
}
},
["tactical"] = {
BGs_VM = {
{2, 1}
},
BGs_WM = {
{2, 1}
},
},
["akmount"] = {
BGs_VM = {
{2, 0}
},
AttPosMods = {
[1] = {
Pos_VM = Vector(-5, 0.4, 3),
Pos_WM = Vector(-0.4, 2, 0.5),
VMScale = 1.2,
}
},
SortOrder = 2,
},
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.5, -0.2),
vm_ang = Angle(0, 0.25, 0),
t = 0.25,
tmax = 0.25,
bones = {
{
bone = "ValveBiped.bolt",
pos = Vector(0, 0, -3),
t0 = 0.01,
t1 = 0.12,
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium", "optic_sniper", "optic_ak"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
InstalledElements = {"tactical"},
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.8,
Pos_VM = Vector(-5.8, 0.2, 4),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 4.25, 0.5),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.bolt",
WMBone = "Box01",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
VMScale = 0.85,
WMScale = 0.85,
Pos_VM = Vector(-0, 21.75, -1.45),
Pos_WM = Vector(0, 29.5, -1.75),
Ang_VM = Angle(90, -90, -90),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
Pos_VM = Vector(-2.25, -0, 22.25),
Pos_WM = Vector(-0.15, 22, -3),
Ang_VM = Angle(90, 0, 180),
Ang_WM = Angle(0, -90, 180),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock", "acc_sling", "acc_duffle", "perk_extendedmag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_4pos"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_an94.remove_clip", path .. "magout_empty.wav")
addsound("tacint_an94.insert_clip", path .. "magin.wav")
addsound("tacint_an94.boltaction", path .. "cock.wav")
addsound("tacint_an94.Buttstock_Back", "tacrp/weapons/ak47/ak47_buttstock_back.wav")

View File

@@ -0,0 +1,373 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "СВД"
SWEP.Category = "[FT] Оружие" // "Tactical RP (Extras)"
SWEP.SubCatTier = "4Consumer"
SWEP.SubCatType = "7Sniper Rifle"
SWEP.Description = "Russian sniper/DMR with low fire rate but great damage and control. Equipped with a 6x scope by default.\nWhile resembling an AK, they are mechanically unrelated."
SWEP.Description_Quote = "Reach out and touch someone the Russian Army way." -- Jagged Alliance: Back in Action (2012) (The gun itself is not a real SVD, but this part of the description is really funny to me)
SWEP.Trivia_Caliber = "7.62x54mmR"
SWEP.Trivia_Manufacturer = "Kalashnikov Concern"
SWEP.Trivia_Year = "1963"
SWEP.Faction = TacRP.FACTION_MILITIA
SWEP.Credits = [[
Model: Rafael De Jongh, Ettubrutesbro
Texture: WangChung
Sound: Ghost597879, King Friday, iFlip
Animation: Tactical Intervention]]
SWEP.ViewModel = "models/weapons/tacint_extras/v_svd.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_svd.mdl"
SWEP.Slot = 2
SWEP.SlotAlt = 3
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 45,
Damage_Min = 75,
Range_Max = 8000,
Range_Min = 2500,
RecoilKick = 5,
RPM = 180,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 30,
Damage_Min = 45,
Range_Min = 600,
Range_Max = 2500,
RPM = 100,
RecoilResetInstant = true,
RecoilResetTime = 0.35,
RecoilDissipationRate = 3,
RecoilMaximum = 3,
RecoilSpreadPenalty = 0.005,
RecoilFirstShotMult = 0.9,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3.5,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.75,
[HITGROUP_RIGHTARM] = 0.75,
[HITGROUP_LEFTLEG] = 0.5,
[HITGROUP_RIGHTLEG] = 0.5,
[HITGROUP_GEAR] = 0.5
},
},
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.SniperRifle
// "ballistics"
SWEP.Damage_Max = 50
SWEP.Damage_Min = 34
SWEP.Range_Min = 2000 // distance for which to maintain maximum damage
SWEP.Range_Max = 6000 // distance at which we drop to minimum damage
SWEP.Penetration = 11 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.775
SWEP.ArmorBonus = 2
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 38000
// misc. shooting
SWEP.Firemode = 1
SWEP.RPM = 150
SWEP.Spread = 0.0002
SWEP.ShootTimeMult = 0.7
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 4
SWEP.RecoilResetTime = 0.22 // time after you stop shooting for recoil to start dissipating
SWEP.RecoilDissipationRate = 4
SWEP.RecoilFirstShotMult = 0.75 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 0.75
SWEP.RecoilKick = 6
SWEP.RecoilStability = 0.6
SWEP.RecoilSpreadPenalty = 0.003
SWEP.HipFireSpreadPenalty = 0.08
SWEP.PeekPenaltyFraction = 0.1
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.85
SWEP.ShootingSpeedMult = 0.75
SWEP.SightedSpeedMult = 0.5
SWEP.ReloadSpeedMult = 0.4
SWEP.AimDownSightsTime = 0.47
SWEP.SprintToFireTime = 0.55
SWEP.Sway = 2.5
SWEP.ScopedSway = 0.1
SWEP.FreeAimMaxAngle = 8.5
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0.5, -2.5, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0.05, -0.35, 0)
SWEP.SightPos = Vector(-4.75, -7.5, -2.7)
SWEP.CorrectivePos = Vector(-0.05, 0, -0.05)
SWEP.CorrectiveAng = Angle(0.65, 0.7, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, -2, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
SWEP.Scope = true
SWEP.ScopeOverlay = Material("tacrp/scopes/pso1_ak.png", "mips smooth") // Material("path/to/overlay")
SWEP.ScopeFOV = 90 / 6
SWEP.ScopeLevels = 1 // 2 = like CS:S
SWEP.ScopeHideWeapon = true
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 10
SWEP.DefaultAmmo = 0
SWEP.Ammo = "ar2"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.Ammo = "ar2"
SWEP.Ammo_TTT = "357"
SWEP.Ammo_Expanded = "ti_rifle"
SWEP.ReloadTimeMult = 1.15
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/svd.mdl"
SWEP.DropMagazineImpact = "metal"
SWEP.ReloadUpInTime = 1.65
SWEP.DropMagazineTime = 0.65
// sounds
local path = "tacint_extras/svd/"
local path2 = "tacrp/weapons/ak47/ak47_"
SWEP.Sound_Shoot = "^" .. path .. "g3sg1-1.wav"
SWEP.Sound_Shoot_Silenced = path2 .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "unholster",
["fire_iron"] = "fire1_M",
["fire"] = {"fire5_M", "fire5_L", "fire5_R"},
["melee"] = {"melee1", "melee2"},
["jam"] = "mid_reload"
}
SWEP.DeployTimeMult = 2.5
// attachments
SWEP.AttachmentElements = {
["sights"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
}
},
["irons"] = {
BGs_VM = {
{1, 2}
},
BGs_WM = {
{1, 2}
},
},
["akmount"] = {
BGs_VM = {
{1, 2}
},
BGs_WM = {
{1, 2}
},
AttPosMods = {
[1] = {
Pos_VM = Vector(-5.5, 0.55, 3),
Pos_WM = Vector(-0.4, 2, 0.5),
}
},
SortOrder = 2,
},
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.8, -0.5),
vm_ang = Angle(0, 1, 0),
t = 0.25,
tmax = 0.25,
bones = {
{
bone = "ValveBiped.bolt",
pos = Vector(0, 0, -3),
t0 = 0.05,
t1 = 0.2,
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"ironsights_sniper", "optic_cqb", "optic_medium", "optic_sniper", "optic_ak2"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
InstalledElements = {"sights"},
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.9,
Pos_VM = Vector(-5.9, 0.24, 5.5),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 5, 1.25),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
VMScale = 0.9,
Pos_VM = Vector(-3.6, 0.24, 39.2),
Pos_WM = Vector(0, 44, -1.5),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
Pos_VM = Vector(-3.25, -0.1, 19),
Pos_WM = Vector(0.3, 20, -1.5),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, -90, -90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_sling", "acc_duffle", "acc_extmag_sniper"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_semi"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_sniper"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_svd.remove_clip", path .. "clipin.wav")
addsound("tacint_svd.insert_clip", path .. "clipout.wav")
addsound("tacint_svd.bolt_back", path .. "bolt_back.wav")
addsound("tacint_svd.bolt_forward", path .. "bolt_forward.wav")

View File

@@ -0,0 +1,370 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "AI AS50"
SWEP.AbbrevName = "AS50"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "1Elite"
SWEP.SubCatType = "7Sniper Rifle"
SWEP.Description = "Semi-automatic AMR that can easily decimate personnel and materiel at any distance. Too heavy to bash with.\nEquipped with a 12x scope by default."
SWEP.Description_Quote = "As seen on Future Weapons."
SWEP.Trivia_Caliber = ".50 BMG"
SWEP.Trivia_Manufacturer = "Accuracy International"
SWEP.Trivia_Year = "2005"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_as50_hq.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_as50.mdl"
SWEP.Slot = 2
SWEP.SlotAlt = 3
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Description = "Semi-automatic anti-materiel rifle with integral bipod.\nEquipped with a 12x scope by default.\nFar too heavy to swing, so bashing is out of the question.",
Damage_Max = 70,
Damage_Min = 140,
Range_Min = 900,
Range_Max = 5000,
},
[TacRP.BALANCE_TTT] = { // this is a buyable weapon in TTT
Description = "Semi-automatic anti-materiel rifle with integral bipod.\nCan kill in up to 2 shots regardless of distance.\nEquipped with a 12x scope by default.",
Damage_Max = 80,
Damage_Min = 150,
Range_Min = 500,
Range_Max = 4000,
RPM = 180,
Penetration = 50,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.675,
[HITGROUP_RIGHTLEG] = 0.675,
[HITGROUP_GEAR] = 0.6
},
},
[TacRP.BALANCE_PVE] = {
Description = "Semi-automatic anti-materiel rifle with integral bipod.\nEquipped with a 12x scope by default.",
Damage_Max = 120,
Damage_Min = 92,
Range_Min = 4000,
Range_Max = 8000,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilDissipationRate = 3,
RecoilMaximum = 20,
RecoilSpreadPenalty = 0.03,
HipFireSpreadPenalty = 0.025,
}
}
// "ballistics"
SWEP.Damage_Max = 150
SWEP.Damage_Min = 110
SWEP.Range_Min = 1200
SWEP.Range_Max = 8000
SWEP.Penetration = 30
SWEP.ArmorPenetration = 1.5
SWEP.ArmorBonus = 6
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5, // nobody is surviving this
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.75
}
SWEP.MuzzleVelocity = 20000
// misc. shooting
SWEP.Firemode = 1
SWEP.RPM = 200
SWEP.Spread = 0
SWEP.RecoilSpreadPenalty = 0.075
SWEP.HipFireSpreadPenalty = 0.1
SWEP.PeekPenaltyFraction = 0.2
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 2
SWEP.RecoilResetTime = 0.25
SWEP.RecoilDissipationRate = 3
SWEP.RecoilFirstShotMult = 1
// SWEP.RecoilMultCrouch = 0.25
SWEP.RecoilVisualKick = 4
SWEP.RecoilKick = 12
SWEP.RecoilStability = 0.6
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.85
SWEP.ShootingSpeedMult = 0.4
SWEP.SightedSpeedMult = 0.5
SWEP.ReloadSpeedMult = 0.2
SWEP.AimDownSightsTime = 0.75
SWEP.SprintToFireTime = 0.65 // multiplies how long it takes to recover from sprinting
SWEP.Sway = 3
SWEP.ScopedSway = 0.25
// SWEP.SwayCrouchMult = 0.15
SWEP.FreeAimMaxAngle = 10
SWEP.Bipod = true
SWEP.BipodRecoil = 0.25
SWEP.BipodKick = 0.35
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_CROSSBOW
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(2, -2, -6)
SWEP.BlindFireAng = Angle(0, 15, 0)
SWEP.BlindFirePos = Vector(2, -2, -4)
SWEP.BlindFireSuicideAng = Angle(0, 135, 0)
SWEP.BlindFireSuicidePos = Vector(-3, 47, -29)
SWEP.CustomizeAng = Angle(50, 15, 0)
SWEP.CustomizePos = Vector(12, 6, -8)
SWEP.SprintAng = Angle(40, -15, 0)
SWEP.SprintPos = Vector(5, 0, -4)
SWEP.SightAng = Angle(0, 0, 0)
SWEP.SightPos = Vector(-4.485, -7.5, -5.16)
SWEP.CorrectivePos = Vector(0.03, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK2
SWEP.HolsterPos = Vector(5, 4, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// scope
SWEP.Scope = true
SWEP.ScopeOverlay = Material("tacrp/scopes/sniper.png", "mips smooth") // Material("path/to/overlay")
SWEP.ScopeFOV = 90 / 12
SWEP.ScopeLevels = 1 // 2 = like CS:S
SWEP.ScopeHideWeapon = true
SWEP.CanMeleeAttack = false
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 5
SWEP.DefaultAmmo = 0
SWEP.Ammo = "357"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.AmmoTTT = "ti_sniper"
SWEP.Ammo_Expanded = "ti_sniper"
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineImpact = "metal"
SWEP.DropMagazineModel = "models/weapons/tacint/magazines/uratio.mdl"
SWEP.ReloadUpInTime = 2.2
SWEP.DropMagazineTime = 0.8
// sounds
local path = "TacRP/weapons/as50/"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_m82_tacrp"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "draw",
["fire"] = {"shoot1", "shoot2"},
["blind_fire"] = {"blind_shoot1", "blind_shoot2"}
}
// attachments
SWEP.AttachmentElements = {
["optic"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
},
SortOrder = 1
},
["irons"] = {
BGs_VM = {
{1, 2}
},
SortOrder = 2
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"ironsights_sniper", "optic_cqb", "optic_medium", "optic_sniper"},
Bone = "ValveBiped._ROOT_AS50",
WMBone = "Box01",
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
InstalledElements = {"optic"},
Pos_VM = Vector(-6.6, -0.1, 7),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 5, 1.75),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "barrel",
Bone = "ValveBiped._ROOT_AS50",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
Pos_VM = Vector(-3.7, 0, 18.5),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(23, 1, -4.5),
Ang_WM = Angle(0, 0, 180),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped._ROOT_AS50",
WMBone = "Box01",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
VMScale = 1.25,
Pos_VM = Vector(-4, -1.6, 18),
Pos_WM = Vector(1.5, 16, -0.5),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, -90, -90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_extmag_sniper", "acc_sling", "acc_duffle"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_semi"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_amr"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("TacInt_as50.Clip_Out", path .. "clip_out.wav")
addsound("TacInt_as50.Clip_In", path .. "clip_in.wav")
addsound("TacInt_as50.Bolt_Back", path .. "bolt_back.wav")
addsound("TacInt_as50.bolt_forward", path .. "bolt_forward.wav")
if engine.ActiveGamemode() == "terrortown" then
SWEP.AutoSpawnable = false
SWEP.Kind = WEAPON_HEAVY
SWEP.CanBuy = { ROLE_TRAITOR, ROLE_DETECTIVE }
SWEP.EquipMenuData = {
type = "Weapon",
desc = "Semi-automatic anti-materiel rifle.\nComes with 10 rounds.\n\nBEWARE: May be visible while holstered!",
}
function SWEP:TTTBought(buyer)
buyer:GiveAmmo(5, "ti_sniper")
end
end

View File

@@ -0,0 +1,334 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Steyr AUG A2"
SWEP.AbbrevName = "AUG A2"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "4Assault Rifle"
SWEP.Description = "Burst bullpup rifle with a generous magazine capacity and great handling."
SWEP.Description_Quote = "\"Welcome to the party, pal.\"" // Die Hard
SWEP.Trivia_Caliber = "5.56x45mm"
SWEP.Trivia_Manufacturer = "Steyr Arms"
SWEP.Trivia_Year = "1977"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_aug.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_aug.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 20,
Damage_Min = 12,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 14,
Damage_Min = 10,
Range_Min = 400,
Range_Max = 1800,
PostBurstDelay = 0.2,
RecoilResetInstant = true,
RecoilResetTime = 0.2,
RecoilSpreadPenalty = 0.004,
RecoilDissipationRate = 18,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 11,
Damage_Min = 7,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilDissipationRate = 15,
RecoilMaximum = 15,
RecoilSpreadPenalty = 0.005,
HipFireSpreadPenalty = 0.007,
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 22
SWEP.Damage_Min = 13
SWEP.Range_Min = 1500
SWEP.Range_Max = 3500
SWEP.Penetration = 7
SWEP.ArmorPenetration = 0.8
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 24000
// misc. shooting
SWEP.Firemodes = {
-3,
1
}
SWEP.RPM = 750
SWEP.RPMMultBurst = 900 / 750
SWEP.Spread = 0.002
SWEP.PostBurstDelay = 0.12
SWEP.RunawayBurst = true
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 12
SWEP.RecoilResetTime = 0.04
SWEP.RecoilDissipationRate = 36
SWEP.RecoilFirstShotMult = 1 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 0.75
SWEP.RecoilKick = 3
SWEP.RecoilStability = 0.25
SWEP.RecoilSpreadPenalty = 0.002
SWEP.HipFireSpreadPenalty = 0.03
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.95
SWEP.ShootingSpeedMult = 0.7
SWEP.SightedSpeedMult = 0.7
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.3
SWEP.SprintToFireTime = 0.25
SWEP.Sway = 1
SWEP.ScopedSway = 0.125
SWEP.FreeAimMaxAngle = 2
// hold types
SWEP.HoldType = "smg"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5.5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0.01, 0.12, 0)
SWEP.SightPos = Vector(-3.93, -6, -4.9)
SWEP.CorrectivePos = Vector(0.12, 0, 0)
SWEP.CorrectiveAng = Angle(0, 0, -1)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 4, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint/magazines/aug.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.7
SWEP.DropMagazineTime = 0.8
// sounds
local path = "tacrp/weapons/aug/aug_"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 115
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_5"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["fire_iron"] = "dryfire",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -1, -0.1),
vm_ang = Angle(0, 0.4, 0),
t = 0.25,
tmax = 0.25,
}
// attachments
SWEP.AttachmentElements = {
["irons"] = {
BGs_VM = {
{1, 1}
},
},
}
SWEP.NoRMR = true
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium", "optic_sniper"},
InstalledElements = {"irons"},
Bone = "ValveBiped.AUG_rootbone",
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 1,
Pos_VM = Vector(-6.4, 0, 1),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(4.5, 1, -7),
Ang_WM = Angle(0, 0, 180),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.AUG_rootbone",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
Pos_VM = Vector(-3.7, 0, 18.5),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(23, 1, -4.5),
Ang_WM = Angle(0, 0, 180),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.AUG_rootbone",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
Pos_VM = Vector(-5, 0, 10),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(14, 1, -6),
Ang_WM = Angle(0, 0, 180),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_sling", "acc_duffle", "perk_extendedmag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_burst"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_aug.insert_clip", path .. "insert_clip.wav")
addsound("tacint_aug.remove_clip", path .. "remove_clip.wav")
addsound("tacint_aug.Handle_FoldDown", path .. "handle_folddown.wav")
addsound("tacint_aug.bolt_lockback", path .. "bolt_lockback.wav")
addsound("tacint_aug.bolt_release", path .. "bolt_release.wav")

View File

@@ -0,0 +1,161 @@
SWEP.AutoSightSlot = nil
SWEP.AutoSightPos = nil
SWEP.AutoSightAng = nil
SWEP.ClientProxyModel = nil
function SWEP:GenerateAutoSight()
local slot
self.AutoSightPos = nil
self.AutoSightAng = nil
for i, k in ipairs(self.Attachments) do
if !k.Installed then continue end
local atttbl = TacRP.GetAttTable(k.Installed)
if atttbl.SightPos and atttbl.SightAng then
slot = i
break
end
end
if !slot then return end
local slottbl = self.Attachments[slot]
if !slottbl.Installed then return end
local bone = slottbl.Bone
local offset_pos = slottbl.Pos_VM
local offset_ang = slottbl.Ang_VM
for _, ele in ipairs(self:GetElements()) do
if !ele.AttPosMods or !ele.AttPosMods[slot] then continue end
if wm then
if ele.AttPosMods[slot].Pos_WM then
offset_pos = ele.AttPosMods[slot].Pos_WM
end
if ele.AttPosMods[slot].Ang_WM then
offset_ang = ele.AttPosMods[slot].Ang_WM
end
if ele.AttPosMods[slot].WMBone then
bone = ele.AttPosMods[slot].WMBone
end
else
if ele.AttPosMods[slot].Pos_VM then
offset_pos = ele.AttPosMods[slot].Pos_VM
end
if ele.AttPosMods[slot].Ang_VM then
offset_ang = ele.AttPosMods[slot].Ang_VM
end
if ele.AttPosMods[slot].Bone then
bone = ele.AttPosMods[slot].Bone
end
end
end
if !bone then return end
local atttbl = TacRP.GetAttTable(slottbl.Installed)
local mdl = ClientsideModel(self.ViewModel)
mdl:SetPos(Vector(0, 0, 0))
mdl:SetAngles(Angle(0, 0, 0))
mdl:SetNoDraw(true)
local anim = self:TranslateSequence("idle")
local seq = mdl:LookupSequence(anim)
mdl:ResetSequence(seq)
mdl:SetupBones()
if !IsValid(mdl) then return end
local boneid = mdl:LookupBone(bone)
local bpos = mdl:GetBoneMatrix(boneid):GetTranslation()
local bang = self.CorrectiveBoneAng and Angle(self.CorrectiveBoneAng) or mdl:GetBoneMatrix(boneid):GetAngles()
SafeRemoveEntity(mdl)
local apos, aang = bpos, bang
apos:Add(bang:Forward() * offset_pos.x)
apos:Add(bang:Right() * offset_pos.y)
apos:Add(bang:Up() * offset_pos.z)
aang:RotateAroundAxis(aang:Right(), offset_ang.p)
aang:RotateAroundAxis(aang:Up(), offset_ang.y)
aang:RotateAroundAxis(aang:Forward(), offset_ang.r)
local moffset = (atttbl.ModelOffset or Vector(0, 0, 0)) * (slottbl.VMScale or 1)
apos:Add(aang:Forward() * moffset.x)
apos:Add(aang:Right() * moffset.y)
apos:Add(aang:Up() * moffset.z)
local vpos, vang = WorldToLocal(apos, aang, Vector(0, 0, 0), Angle(0, 0, 0))
local x = vpos.x
local y = vpos.y
local z = vpos.z
vpos.x = -y
vpos.y = x
vpos.z = z
vpos = vpos + (self.CorrectivePos or Vector(0, 0, 0))
vang = vang + (self.CorrectiveAng or Angle(0, 0, 0))
self.AutoSightPos, self.AutoSightAng = -vpos, -vang
end
function SWEP:GetSightPositions()
local apos, aang = self.AutoSightPos, self.AutoSightAng
if apos and aang then
return apos, aang
elseif self:GetOwner() != LocalPlayer() then
self:GenerateAutoSight() -- Not generated for spectators so must be done here
return self.AutoSightPos or self.SightPos, self.AutoSightAng or self.SightAng
else
return self.SightPos, self.SightAng
end
end
function SWEP:GetExtraSightPosition()
local epos
local eang
local scale = 1
for i, k in ipairs(self.Attachments) do
if !k.Installed then continue end
local atttbl = TacRP.GetAttTable(k.Installed)
if atttbl.SightPos and atttbl.SightAng then
epos = atttbl.SightPos
eang = atttbl.SightAng
scale = k.VMScale or 1
break
end
end
local pos = Vector(0, 0, 0)
local ang = Angle(0, 0, 0)
if epos then
pos:Set(epos)
end
if eang then
ang:Set(eang)
end
pos = pos * scale
return pos, ang
end

View File

@@ -0,0 +1,35 @@
SWEP.SmoothedMagnification = 1
function SWEP:CalcView(ply, pos, ang, fov)
local rec = (self:GetLastRecoilTime() + self:RecoilDuration()) - CurTime()
rec = math.max(rec, 0)
rec = rec * (self:GetValue("RecoilKick") + 1) * (self:GetRecoilAmount() / self:GetValue("RecoilMaximum")) ^ 0.75
if !game.SinglePlayer() then
rec = rec * 0.5 -- ???????????????
end
if rec > 0 then
ang.r = ang.r + (math.sin(CurTime() * 70.151) * rec)
end
local mag = Lerp(self:GetSightAmount() ^ 3, 1, self:GetMagnification())
if self:GetHoldBreathAmount() > 0 then
mag = mag * (1 + self:GetHoldBreathAmount() * 0.15)
end
local diff = math.abs(self.SmoothedMagnification - mag)
self.SmoothedMagnification = math.Approach(self.SmoothedMagnification, mag, FrameTime() * diff * (self.SmoothedMagnification > mag and 10 or 5))
fov = fov / self.SmoothedMagnification
self.TacRPLastFOV = fov
fov = fov - rec
return pos, ang, fov
end

View File

@@ -0,0 +1,259 @@
local rt_w = 426
local rt_h = 240
local rtmat = GetRenderTarget("tacrp_pipscope", rt_w, rt_h, false)
local lastblindfire = false
local blindfiretime = 0
local csm_boot_1 = Material("tacrp/hud/cornershot_boot_1.png", "mips smooth")
local csm_boot_2 = Material("tacrp/hud/cornershot_boot_2.png", "mips smooth")
local csm_boot_3 = Material("tacrp/hud/cornershot_boot_3.png", "mips smooth")
local csm_1 = Material("tacrp/hud/cornershot_1.png", "mips smooth")
local csm_2 = Material("tacrp/hud/cornershot_2.png", "mips smooth")
local csm_n_1 = Material("tacrp/hud/cornershot_n_1.png", "mips smooth")
local csm_n_2 = Material("tacrp/hud/cornershot_n_2.png", "mips smooth")
local noise1 = Material("tacrp/hud/noise1.png")
local noise2 = Material("tacrp/hud/noise2.png")
local noise3 = Material("tacrp/hud/noise3.png")
local noise4 = Material("tacrp/hud/noise4.png")
local noisemats = {
noise1,
noise2,
noise3,
noise4
}
local lastrendertime = 0
local fps = 30
function SWEP:DoRT()
if !self:GetBlindFire() and !IsValid(self:GetCornershotEntity()) then lastblindfire = false return end
if TacRP.OverDraw then return end
if !lastblindfire then
blindfiretime = 0
end
if lastrendertime > CurTime() - (1 / fps) then return end
local angles = self:GetShootDir()
local origin = self:GetMuzzleOrigin()
if IsValid(self:GetCornershotEntity()) then
origin = self:GetCornershotEntity():LocalToWorld(self:GetCornershotEntity().CornershotOffset)
angles = self:GetCornershotEntity():LocalToWorldAngles(self:GetCornershotEntity().CornershotAngles)
TacRP.CornerCamDrawSelf = true
elseif self:GetBlindFireMode() == TacRP.BLINDFIRE_KYS then
local bone = self:GetOwner():LookupBone("ValveBiped.Bip01_R_Hand")
if bone then
local pos, ang = self:GetOwner():GetBonePosition(bone)
angles = ang
angles:RotateAroundAxis(angles:Forward(), 180)
origin = pos
TacRP.CornerCamDrawSelf = true
end
end
local rt = {
x = 0,
y = 0,
w = rt_w,
h = rt_h,
aspect = 4 / 3,
angles = angles,
origin = origin,
drawviewmodel = false,
fov = 40,
znear = 6
}
render.PushRenderTarget(rtmat, 0, 0, rt_w, rt_h)
if blindfiretime >= 1 or blindfiretime == 0 then
TacRP.OverDraw = true
render.RenderView(rt)
TacRP.OverDraw = false
end
TacRP.CornerCamDrawSelf = false
if self:GetTactical() then
DrawColorModify({
["$pp_colour_addr"] = 0.25 * 132 / 255,
["$pp_colour_addg"] = 0.25 * 169 / 255,
["$pp_colour_addb"] = 0.25 * 154 / 255,
["$pp_colour_brightness"] = 0.2,
["$pp_colour_contrast"] = 0.85,
["$pp_colour_colour"] = 0.95,
["$pp_colour_mulr"] = 0,
["$pp_colour_mulg"] = 0,
["$pp_colour_mulb"] = 0
})
else
DrawColorModify({
["$pp_colour_addr"] = 0.25 * 132 / 255,
["$pp_colour_addg"] = 0.25 * 169 / 255,
["$pp_colour_addb"] = 0.25 * 154 / 255,
["$pp_colour_brightness"] = -0.1,
["$pp_colour_contrast"] = 5,
["$pp_colour_colour"] = 0,
["$pp_colour_mulr"] = 0,
["$pp_colour_mulg"] = 0,
["$pp_colour_mulb"] = 0
})
DrawBloom(0.25, 0.5, 16, 8, 1, 1, 1, 1, 1)
end
-- if blindfiretime < 0.33 then
-- surface.SetMaterial(csm_boot_1)
-- elseif blindfiretime < 0.66 then
-- surface.SetMaterial(csm_boot_2)
-- elseif blindfiretime < 1.25 then
-- surface.SetMaterial(csm_boot_3)
-- else
-- end
cam.Start2D()
render.ClearDepth()
if blindfiretime < 1 then
if blindfiretime < 0.75 then
surface.SetDrawColor(255, 255, 255)
surface.SetMaterial(noisemats[math.random(#noisemats)])
surface.DrawTexturedRect(0, 0, rt_w, rt_h)
else
surface.SetDrawColor(0, 0, 0)
surface.DrawRect(0, 0, rt_w, rt_h)
end
DrawColorModify({
["$pp_colour_addr"] = 0.25 * 132 / 255,
["$pp_colour_addg"] = 0.25 * 169 / 255,
["$pp_colour_addb"] = 0.25 * 154 / 255,
["$pp_colour_brightness"] = 0.2,
["$pp_colour_contrast"] = 0.85,
["$pp_colour_colour"] = 0.95,
["$pp_colour_mulr"] = 0,
["$pp_colour_mulg"] = 0,
["$pp_colour_mulb"] = 0
})
end
if blindfiretime < 0.2 then
surface.SetMaterial(csm_boot_1)
elseif blindfiretime < 0.4 then
surface.SetMaterial(csm_boot_2)
elseif blindfiretime < 0.6 then
surface.SetMaterial(csm_boot_3)
else
if self:GetTactical() then
if math.sin(CurTime() * 3) > 0.5 then
surface.SetMaterial(csm_1)
else
surface.SetMaterial(csm_2)
end
else
if math.sin(CurTime() * 3) > 0.5 then
surface.SetMaterial(csm_n_1)
else
surface.SetMaterial(csm_n_2)
end
end
end
surface.SetDrawColor(255, 255, 255)
surface.DrawTexturedRect(0, 0, rt_w, rt_h)
cam.End2D()
render.PopRenderTarget()
blindfiretime = blindfiretime + (math.random(0, 5) * math.random(0, 5) * (1 / fps) / 6.25)
lastblindfire = true
lastrendertime = CurTime()
end
function SWEP:DoCornershot()
if !self:GetBlindFire() and !IsValid(self:GetCornershotEntity()) then lastblindfire = false return end
local w = TacRP.SS(640 / 4)
local h = TacRP.SS(480 / 4)
local x = (ScrW() - w) / 2
local y = (ScrH() - h) / 2
-- y = y + (ScrH() / 4)
render.DrawTextureToScreenRect(rtmat, x, y, w, h)
end
hook.Add("ShouldDrawLocalPlayer", "TacRP_CornerCamDrawSelf", function(ply)
if TacRP.CornerCamDrawSelf then
return true
end
end)
SWEP.NearWallTick = 0
SWEP.NearWallCached = false
local traceResults = {}
local traceData = {
start = true,
endpos = true,
filter = true,
mask = MASK_SHOT_HULL,
output = traceResults
}
local VECTOR = FindMetaTable("Vector")
local vectorAdd = VECTOR.Add
local vectorMul = VECTOR.Mul
local angleForward = FindMetaTable("Angle").Forward
local entityGetOwner = FindMetaTable("Entity").GetOwner
function SWEP:GetNearWallAmount()
local now = engine.TickCount()
if !TacRP.ConVars["nearwall"]:GetBool() or LocalPlayer():GetMoveType() == MOVETYPE_NOCLIP then
return 0
end
if self.NearWallTick == now then
return self.NearWallCached
end
local length = 32
local startPos = self:GetMuzzleOrigin()
local endPos = angleForward(self:GetShootDir())
vectorMul(endPos, length)
vectorAdd(endPos, startPos)
traceData.start = startPos
traceData.endpos = endPos
traceData.filter = entityGetOwner(self)
util.TraceLine(traceData)
local hit = 1 - traceResults.Fraction
self.NearWallCached = hit
self.NearWallTick = now
return hit
end
function SWEP:ThinkNearWall()
self:GetNearWallAmount()
end

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,242 @@
local glyphs = {
["MOUSE1"] = Material("tacrp/glyphs/shared_mouse_l_click_lg.png", "mips smooth"),
["MOUSE2"] = Material("tacrp/glyphs/shared_mouse_r_click_lg.png", "mips smooth"),
["MOUSE3"] = Material("tacrp/glyphs/shared_mouse_mid_click_lg.png", "mips smooth"),
["MOUSE4"] = Material("tacrp/glyphs/shared_mouse_4_lg.png", "mips smooth"),
["MOUSE5"] = Material("tacrp/glyphs/shared_mouse_5_lg.png", "mips smooth"),
["MWHEELUP"] = Material("tacrp/glyphs/shared_mouse_scroll_up_lg.png", "mips smooth"),
["MWHEELDOWN"] = Material("tacrp/glyphs/shared_mouse_scroll_down_lg.png", "mips smooth"),
}
local rename = {
KP_INS = "KP 0",
KP_END = "KP 1",
KP_DOWNARROW = "KP 2",
KP_PGDN = "KP 3",
KP_LEFTARROW = "KP 4",
KP_5 = "KP 5",
KP_RIGHTARROW = "KP 6",
KP_HOME = "KP 7",
KP_UPARROW = "KP 8",
KP_PGUP = "KP 9",
KP_SLASH = "KP /",
KP_MULTIPLY = "KP *",
KP_MINUS = "KP -",
KP_PLUS = "KP +",
KP_ENTER = "KP ENTER",
KP_DEL = "KP .",
}
local mat_bipod = Material("tacrp/hud/bipod.png", "mips smooth")
SWEP.CachedCapabilities = {}
function SWEP:GetHintCapabilities()
self.CachedCapabilities = {}
if self:GetValue("PrimaryMelee") then
self.CachedCapabilities["+attack"] = {so = 0, str = "hint.melee"}
elseif self:GetValue("PrimaryGrenade") then
self.CachedCapabilities["+attack"] = {so = 0, str = "hint.quicknade.over"}
self.CachedCapabilities["+attack2"] = {so = 0.1, str = "hint.quicknade.under"}
end
-- hopefully you don't need me to tell you how to shoot a gun
local bind_customize = "+menu_context"
if TacRP.GetKeyIsBound("+tacrp_customize") then
bind_customize = "+tacrp_customize"
end
if self:GetScopeLevel() != 0 then
if TacRP.ConVars["togglepeek"]:GetBool() then
self.CachedCapabilities[bind_customize] = {so = 2, str = "hint.peek.toggle"}
else
self.CachedCapabilities[bind_customize] = {so = 2, str = "hint.peek.hold"}
end
if self:CanHoldBreath() then
self.CachedCapabilities["+speed"] = {so = 2.1, str = "hint.hold_breath"}
end
elseif #self.Attachments > 0 then
self.CachedCapabilities[bind_customize] = {so = 1, str = "hint.customize"}
else
self.CachedCapabilities[bind_customize] = {so = 1, str = "hint.inspect"}
end
if self:GetFiremodeAmount() > 1 and !self:GetSafe() then
self.CachedCapabilities["+use/+reload"] = {so = 11, str = "hint.firemode"}
end
if self:GetFiremodeAmount() > 0 and !self:DoForceSightsBehavior() then
if self:GetSafe() then
self.CachedCapabilities["+use/+attack2"] = {so = 12, str = "hint.safety.turn_off"}
else
self.CachedCapabilities["+use/+attack2"] = {so = 12, str = "hint.safety.turn_on"}
end
end
if self:GetValue("CanMeleeAttack") and !self:GetValue("PrimaryMelee") then
local bind = "+use/+attack"
if TacRP.GetKeyIsBound("+tacrp_melee") then
bind = TacRP.GetBindKey("+tacrp_melee")
elseif self:DoOldSchoolScopeBehavior() then
bind = "+attack2"
end
self.CachedCapabilities[bind] = {so = 30, str = "hint.melee"}
end
if self:GetValue("CanToggle") and TacRP.ConVars["toggletactical"]:GetBool() then
local tactical_text = self:GetValue("CustomTacticalHint") or TacRP:GetPhrase("hint.toggle_tactical", {TacRP:TryTranslate(self:GetValue("TacticalName") or "hint.tac")})
local bind = nil
if TacRP.GetKeyIsBound("+tacrp_tactical") then
bind = "+tacrp_tactical"
end
if TacRP.ConVars["flashlight_alt"]:GetBool() then
self.CachedCapabilities[bind or "+walk/impulse 100"] = {so = 31, str = tactical_text}
self.CachedCapabilities["impulse 100"] = {so = 32, str = "hint.hl2_flashlight"}
else
self.CachedCapabilities[bind or "impulse 100"] = {so = 31, str = tactical_text}
self.CachedCapabilities["+walk/impulse 100"] = {so = 32, str = "hint.hl2_flashlight"}
end
end
-- blindfire / quickthrow
if self:GetValue("CanBlindFire") and self:GetScopeLevel() == 0 and !self:GetSafe() then
if TacRP.ConVars["blindfiremenu"]:GetBool() then
self.CachedCapabilities["+zoom"] = {so = 39, str = "hint.blindfire.menu"}
else
if self:GetOwner():KeyDown(IN_ZOOM) then
self.CachedCapabilities = {}
self.CachedCapabilities["+zoom/+forward"] = {so = 39, str = "hint.blindfire.up"}
self.CachedCapabilities["+zoom/+moveleft"] = {so = 39.1, str = "hint.blindfire.left"}
self.CachedCapabilities["+zoom/+moveright"] = {so = 39.2, str = "hint.blindfire.right"}
self.CachedCapabilities["+zoom/+back"] = {so = 39.3, str = "hint.blindfire.cancel"}
if !TacRP.ConVars["idunwannadie"]:GetBool() then
self.CachedCapabilities["+zoom/+speed/+walk"] = {so = 39.4, str = "hint.blindfire.kys"}
end
return self.CachedCapabilities
else
self.CachedCapabilities["+zoom"] = {so = 39, str = "hint.blindfire"}
end
end
end
if self:IsQuickNadeAllowed() then
local bound1, bound2 = TacRP.GetKeyIsBound("+grenade1"), TacRP.GetKeyIsBound("+grenade2")
if bound1 then
self.CachedCapabilities["+grenade1"] = {so = 35, str = "hint.quicknade.throw"}
end
if bound2 then
if TacRP.ConVars["nademenu"]:GetBool() then
if TacRP.ConVars["nademenu_click"]:GetBool() and self.GrenadeMenuAlpha == 1 then
self.CachedCapabilities = {}
self.CachedCapabilities["+grenade2"] = {so = 36, str = "hint.quicknade.menu"}
self.CachedCapabilities["+grenade2/+attack"] = {so = 36.1, str = "hint.quicknade.over"}
self.CachedCapabilities["+grenade2/+attack2"] = {so = 36.2, str = "hint.quicknade.under"}
if TacRP.AreTheGrenadeAnimsReadyYet then
self.CachedCapabilities["+grenade2/MOUSE3"] = {so = 36.3, str = "hint.quicknade.pull_out"}
end
-- if TacRP.GetKeyIsBound("+grenade1") then
-- self.CachedCapabilities["+grenade1"] = {so = 36.4, str = "Quickthrow"}
-- end
return self.CachedCapabilities
else
self.CachedCapabilities["+grenade2"] = {so = 36, str = "hint.quicknade.menu"}
end
else
self.CachedCapabilities["+grenade2"] = {so = 36, str = "hint.quicknade.next"}
self.CachedCapabilities["+walk/+grenade2"] = {so = 37, str = "hint.quicknade.prev"}
end
end
if !bound2 and !bound1 then
self.CachedCapabilities["+grenade1"] = {so = 36, str = "hint.quicknade.throw"}
end
end
if engine.ActiveGamemode() == "terrortown" then
self.CachedCapabilities["+use/+zoom"] = {so = 1001, str = "hint.ttt.radio"}
self.CachedCapabilities["+use/+menu_context"] = {so = 1002, str = "hint.ttt.shop"}
end
self:RunHook("Hook_GetHintCapabilities", self.CachedCapabilities)
return self.CachedCapabilities
end
SWEP.LastHintLife = 0
function SWEP:DrawHints()
if LocalPlayer() != self:GetOwner() then return end
local a = TacRP.ConVars["hints_always"]:GetBool() and 1 or math.Clamp(((self.LastHintLife + 4) - CurTime()) / 1, 0, 1)
if a <= 0 then return end
local font = TacRP.ConVars["hints_altfont"]:GetBool() and "TacRP_Myriad_Pro_8" or "TacRP_HD44780A00_5x8_5"
local caps = self:GetHintCapabilities()
local clr_w = Color(255, 255, 255, a * 255)
local x, y = TacRP.SS(4), ScrH() / 2
local row = TacRP.SS(12)
local glyphsize = TacRP.SS(8)
local w, h = TacRP.SS(100), table.Count(caps) * row
surface.SetDrawColor(0, 0, 0, 150 * a)
TacRP.DrawCorneredBox(x, y - h / 2, w, h, clr_w)
local x2, x3 = TacRP.SS(6), TacRP.SS(30)
local y2 = y - h / 2
for k, v in SortedPairsByMemberValue(self.CachedCapabilities, "so") do
local keys = string.Explode("/", k, false)
surface.SetDrawColor(clr_w)
local x_glyph = x2
local y_glyph = y2 + row / 2
for i = 1, #keys do
local key = TacRP.GetBindKey(keys[i])
if glyphs[key] then
surface.SetMaterial(glyphs[key])
surface.DrawTexturedRect(x + x_glyph, y_glyph - glyphsize / 2, TacRP.SS(8), glyphsize)
-- surface.DrawOutlinedRect(x + x_glyph, y_glyph - glyphsize / 2, glyphsize, glyphsize, 2)
x_glyph = x_glyph + glyphsize
else
key = rename[key] or key
local addw = string.len(key) * TacRP.SS(3.5) + TacRP.SS(5)
surface.DrawOutlinedRect(x + x_glyph, y_glyph - glyphsize / 2, addw, glyphsize, 1)
draw.SimpleText(key, "TacRP_HD44780A00_5x8_5", x + x_glyph + addw / 2, y_glyph, clr_w, TEXT_ALIGN_CENTER, TEXT_ALIGN_CENTER)
x_glyph = x_glyph + addw
end
if i < #keys then
x_glyph = x_glyph + TacRP.SS(2)
else
x_glyph = x_glyph + TacRP.SS(4)
end
end
draw.SimpleText(TacRP:TryTranslate(v.str), font, x + math.max(x3, x_glyph), y2 + row / 2, clr_w, TEXT_ALIGN_LEFT, TEXT_ALIGN_CENTER)
y2 = y2 + row
end
end
function SWEP:DrawBipodHint(x, y, s)
surface.SetDrawColor(0, 0, 0, 150)
TacRP.DrawCorneredBox(x, y - s / 2, s, s, color_white)
if self:CanBipod() then
if self:GetInBipod() then
surface.SetDrawColor(255, 255, 255, 255)
else
local c = math.sin(CurTime() * 8) * 25 + 175
surface.SetDrawColor(c, c, c, 255)
end
surface.SetMaterial(mat_bipod)
surface.DrawTexturedRect(x, y - s / 2, s, s)
if !self:GetInBipod() then
surface.SetDrawColor(255, 255, 255, 255)
surface.SetMaterial(glyphs["MOUSE2"])
surface.DrawTexturedRect(x + s * 0.3333, y + s * 0.15, s / 3, s / 3)
end
else
surface.SetDrawColor(100, 100, 100, 255)
surface.SetMaterial(mat_bipod)
surface.DrawTexturedRect(x, y - s / 2, s, s)
end
end

View File

@@ -0,0 +1,84 @@
function SWEP:DoHolosight(mdl)
if TacRP.OverDraw then return end
if self:GetSightAmount() <= 0 then return end
local ref = 64
render.UpdateScreenEffectTexture()
render.ClearStencil()
render.SetStencilEnable(true)
render.SetStencilCompareFunction(STENCIL_ALWAYS)
render.SetStencilPassOperation(STENCIL_REPLACE)
render.SetStencilFailOperation(STENCIL_KEEP)
render.SetStencilZFailOperation(STENCIL_KEEP)
render.SetStencilWriteMask(255)
render.SetStencilTestMask(255)
render.SetBlend(0)
render.SetStencilReferenceValue(ref)
mdl:DrawModel()
render.SetBlend(1)
render.SetStencilPassOperation(STENCIL_KEEP)
render.SetStencilCompareFunction(STENCIL_EQUAL)
-- cam.Start2D()
-- surface.SetDrawColor(255, 255, 255)
-- surface.DrawRect(0, 0, ScrW(), ScrH())
-- render.SetColorMaterial()
-- render.DrawScreenQuad()
local img = self:GetValue("Holosight")
if img then
local pos = self:GetOwner():EyePos()
local dir = (self:GetShootDir() + self:GetOwner():GetViewPunchAngles() * 0.5):Forward() -- mdl:GetAngles():Forward()
local size = 512 * TacRP.HoloSS
pos = pos + dir * 9000
-- cam.Start3D()
local eyedist = WorldToLocal(mdl:GetPos(), mdl:GetAngles(), EyePos(), EyeAngles()).x
render.DepthRange(0, 0.005 + (0.0005 * eyedist / 20))
render.SetMaterial(img)
render.DrawQuadEasy(pos, -dir, size, size, Color(255, 255, 255), 180)
-- cam.End3D()
-- local toscreen = pos:ToScreen()
-- local x = toscreen.x
-- local y = toscreen.y
-- local ss = TacRP.SS(32)
-- local sx = x - (ss / 2)
-- local sy = y - (ss / 2)
-- local shakey = math.min(cross * 35, 3)
-- sx = sx + math.Round(math.Rand(-shakey, shakey))
-- sy = sy + math.Round(math.Rand(-shakey, shakey))
-- surface.SetMaterial(img)
-- surface.SetDrawColor(255, 255, 255, 255)
-- surface.DrawTexturedRect(sx, sy, ss, ss)
-- surface.SetDrawColor(0, 0, 0)
-- surface.DrawRect(0, 0, w, sy)
-- surface.DrawRect(0, sy + ss, w, h - sy)
-- surface.DrawRect(0, 0, sx, h)
-- surface.DrawRect(sx + ss, 0, w - sx, h)
end
-- cam.End2D()
render.SetStencilEnable(false)
end

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,140 @@
local lasermat = Material("effects/laser1")
local flaremat = Material("effects/whiteflare")
function SWEP:DrawLaser(pos, ang, strength, thirdperson)
strength = strength or 1
local alwaysacc = self:GetValue("LaserAlwaysAccurate")
local behavior = (self:GetValue("ScopeHideWeapon") and self:IsInScope())
local vm = self:GetOwner():IsPlayer() and self:GetOwner():GetViewModel()
local curr_seq = IsValid(vm) and vm:GetSequenceName(vm:GetSequence())
local delta = behavior and 1 or 0
if IsValid(vm) and (alwaysacc or TacRP.ConVars["true_laser"]:GetBool()) and (self:GetBlindFireMode() <= 1) and !self:GetCustomize() and !behavior then
local d1 = (CurTime() - self:GetNextSecondaryFire()) / 1
if alwaysacc then
d1 = 1
elseif TacRP.ConVars["laser_beam"]:GetBool() then
d1 = math.min((CurTime() - self:GetNextPrimaryFire()) / 2, (CurTime() - self:GetNextSecondaryFire()) / 1)
elseif self:GetValue("RPM") < 120 then
d1 = math.min((CurTime() - self:GetNextPrimaryFire()) / 0.5, (CurTime() - self:GetNextSecondaryFire()) / 1)
end
local d2 = (curr_seq == "reload_start") and 0 or 1
local d3 = (1 - math.min(self:GetAnimLockTime() - CurTime()) / vm:SequenceDuration(vm:GetSequence()))
local d4 = self:CanShootInSprint() and 1 or (1 - self:GetSprintDelta()) ^ 2
if self:DoForceSightsBehavior() then d4 = self:GetSprintDelta() * self:GetSightDelta() end
local cutoff = 0.85
d3 = math.max(d3 - cutoff, 0) / (1 - cutoff)
delta = math.Clamp(self:GetReloading() and 0 or math.min(d1, d2, d3, d4), 0, 1)
end
local pos_tr = self:GetMuzzleOrigin()
if behavior then
ang = self:GetShootDir()
else
ang = LerpAngle(delta, ang, self:GetShootDir())
end
local tr = util.TraceLine({
start = pos_tr,
endpos = pos_tr + (ang:Forward() * 30000),
mask = MASK_OPAQUE,
filter = self:GetOwner()
})
if tr.StartSolid then return end
local laser_pos = tr.HitPos + tr.HitNormal
local adjusted_pos = thirdperson and laser_pos or TacRP.FormatViewModelAttachment(self.ViewModelFOV, laser_pos, false)
laser_pos = LerpVector(delta, laser_pos, adjusted_pos)
if behavior then
cam.Start3D()
pos = pos - (ang:Forward() * 256)
end
local col = self:GetValue("LaserColor")
if TacRP.ConVars["laser_beam"]:GetBool() then
local width = math.Rand(0.1, 0.2) * strength
render.SetMaterial(lasermat)
render.DrawBeam(pos, laser_pos, width * 0.3, 0, 1, Color(200, 200, 200))
render.DrawBeam(pos, laser_pos, width, 0, 1, col)
end
if tr.Hit and !tr.HitSky then
local mul = strength
local rad = math.Rand(4, 6) * mul
render.SetMaterial(flaremat)
render.DrawSprite(laser_pos, rad, rad, col)
render.DrawSprite(laser_pos, rad * 0.3, rad * 0.3, Color(200, 200, 200))
debugoverlay.Cross(tr.HitPos, 4, FrameTime() * 2, col)
end
if behavior then
cam.End3D()
end
end
function SWEP:DrawLasers(wm)
wm = wm or false
if self.Laser and self:GetTactical() then
local power = self.LaserPower or 2
if wm and self.LaserQCAttachmentWM then
local att = self:GetAttachment(self.LaserQCAttachmentWM)
if att then
self:DrawLaser(att.Pos, att.Ang, power, true)
end
elseif IsValid(self:GetOwner():GetViewModel()) and self.LaserQCAttachmentVM then
local vm = self:GetOwner():GetViewModel()
local att = vm:GetAttachment(self.LaserQCAttachmentVM)
if att then
local pos = TacRP.FormatViewModelAttachment(self.ViewModelFOV, att.Pos, false)
self:DrawLaser(pos, att.Ang, power)
end
end
end
for i, k in pairs(self.Attachments) do
if !k.Installed then continue end
local atttbl = TacRP.GetAttTable(k.Installed)
local power = atttbl.LaserPower or 2
if atttbl.Laser and self:GetTactical() then
if wm then
if atttbl.LaserQCAttachmentWM then
local att = self:GetAttachment(atttbl.LaserQCAttachmentWM)
if att then
self:DrawLaser(att.Pos, self:GetOwner():IsPlayer() and self:GetShootDir() or att.Ang, power, true)
end
elseif IsValid(k.WModel) then
if self:GetOwner():IsPlayer() then
self:DrawLaser(k.WModel:GetPos(), self:GetShootDir(), power, true)
else
self:DrawLaser(k.WModel:GetPos(), k.WModel:GetAngles(), power, true)
end
end
else
if IsValid(self:GetOwner():GetViewModel()) and atttbl.LaserQCAttachmentVM then
local vm = self:GetOwner():GetViewModel()
local att = vm:GetAttachment(atttbl.LaserQCAttachmentVM)
if att then
local pos = TacRP.FormatViewModelAttachment(self.ViewModelFOV, att.Pos, false)
self:DrawLaser(pos, att.Ang, power)
end
elseif IsValid(k.VModel) then
self:DrawLaser(k.VModel:GetPos() + (k.VModel:GetAngles():Up() * 0.75), k.VModel:GetAngles(), power)
end
end
end
end
end

View File

@@ -0,0 +1,333 @@
SWEP.Flashlights = {} -- tracks projectedlights
-- {{att = int, light = ProjectedTexture}}
function SWEP:GetHasFlashlights()
for i, k in pairs(self.Attachments) do
if !k.Installed then continue end
local atttbl = TacRP.GetAttTable(k.Installed)
if atttbl.Flashlight then return true end
end
return false
end
function SWEP:CreateFlashlights()
self:KillFlashlights()
self.Flashlights = {}
local total_lights = 0
for i, k in pairs(self.Attachments) do
if !k.Installed then continue end
local atttbl = TacRP.GetAttTable(k.Installed)
if atttbl.Flashlight then
local newlight = {
att = i,
light = ProjectedTexture(),
col = Color(255, 255, 255),
br = 4,
}
total_lights = total_lights + 1
local l = newlight.light
if !IsValid(l) then continue end
table.insert(self.Flashlights, newlight)
l:SetFOV(atttbl.FlashlightFOV or 60)
l:SetFarZ(atttbl.FlashlightFarZ or 1024)
l:SetNearZ(4)
l:SetQuadraticAttenuation(100)
l:SetColor(atttbl.FlashlightColor or color_white)
l:SetTexture("effects/flashlight001")
l:SetBrightness(atttbl.FlashlightBrightness or 1.5)
l:SetEnableShadows(true)
l:Update()
local g_light = {
Weapon = self,
ProjectedTexture = l
}
table.insert(TacRP.FlashlightPile, g_light)
end
end
if total_lights > 2 then -- you are a madman
for i, k in pairs(self.Flashlights) do
if k.light:IsValid() then k.light:SetEnableShadows(false) end
end
end
end
function SWEP:KillFlashlights()
self:KillFlashlightsVM()
-- self:KillFlashlightsWM()
end
function SWEP:KillFlashlightsVM()
if !self.Flashlights then return end
for i, k in pairs(self.Flashlights) do
if k.light and k.light:IsValid() then
k.light:Remove()
end
end
self.Flashlights = nil
end
function SWEP:DrawFlashlightsVM()
if !self:GetTactical() then
self:KillFlashlights()
return
end
if !self.Flashlights then
self:CreateFlashlights()
end
for i, k in pairs(self.Flashlights) do
local model = self.Attachments[k.att].VModel
local pos, ang
if !IsValid(model) then
pos = self:GetOwner():EyePos()
ang = self:GetOwner():EyeAngles()
else
pos = model:GetPos()
ang = model:GetAngles()
end
local tr = util.TraceLine({
start = self:GetOwner():EyePos(),
endpos = self:GetOwner():EyePos() - -ang:Forward() * 128,
mask = MASK_OPAQUE,
filter = LocalPlayer(),
})
if tr.Fraction < 1 then -- We need to push the flashlight back
local tr2 = util.TraceLine({
start = self:GetOwner():EyePos(),
endpos = self:GetOwner():EyePos() + -ang:Forward() * 128,
mask = MASK_OPAQUE,
filter = LocalPlayer(),
})
-- push it as back as the area behind us allows
pos = pos + -ang:Forward() * 128 * math.min(1 - tr.Fraction, tr2.Fraction)
end
-- ang:RotateAroundAxis(ang:Up(), 90)
k.light:SetPos(pos)
k.light:SetAngles(ang)
k.light:Update()
-- local col = k.col
-- local dl = DynamicLight(self:EntIndex())
-- if dl then
-- dl.pos = pos
-- dl.r = col.r
-- dl.g = col.g
-- dl.b = col.b
-- dl.brightness = k.br or 2
-- -- print(z / maxz)
-- dl.Decay = 1000 / 0.1
-- dl.dietime = CurTime() + 0.1
-- dl.size = (k.br or 2) * 64
-- end
end
end
function SWEP:DrawFlashlightsWM()
if self:GetOwner() != LocalPlayer() then return end
if !self.Flashlights then
self:CreateFlashlights()
end
for i, k in ipairs(self.Flashlights) do
local model = (k.slottbl or {}).WModel
if !IsValid(model) then continue end
local pos, ang
if !model then
pos = self:GetOwner():EyePos()
ang = self:GetOwner():EyeAngles()
else
pos = model:GetPos()
ang = model:GetAngles()
end
-- ang:RotateAroundAxis(ang:Up(), 90)
local tr = util.TraceLine({
start = pos,
endpos = pos + ang:Forward() * 16,
mask = MASK_OPAQUE,
filter = LocalPlayer(),
})
if tr.Fraction < 1 then -- We need to push the flashlight back
local tr2 = util.TraceLine({
start = pos,
endpos = pos - ang:Forward() * 16,
mask = MASK_OPAQUE,
filter = LocalPlayer(),
})
-- push it as back as the area behind us allows
pos = pos + -ang:Forward() * 16 * math.min(1 - tr.Fraction, tr2.Fraction)
else
pos = tr.HitPos
end
k.light:SetPos(pos)
k.light:SetAngles(ang)
k.light:Update()
end
end
local flaremat = Material("tacrp/particle_flare")
function SWEP:DrawFlashlightGlare(pos, ang, strength, dot)
strength = strength or 1
local diff = EyePos() - pos
local wep = LocalPlayer():GetActiveWeapon()
--local dot = math.Clamp((-ang:Forward():Dot(EyeAngles():Forward()) - 0.707) / (1 - 0.707), 0, 1) ^ 2
if TacRP.ConVars["flashlight_blind"]:GetBool() then
dot = dot ^ 4
local tr = util.QuickTrace(pos, diff, {self:GetOwner(), LocalPlayer()})
local s = math.Clamp(1 - diff:Length() / 328, 0, 1) ^ 1 * dot * 2000 * math.Rand(0.95, 1.05)
if IsValid(wep) and wep.ArcticTacRP and wep:IsInScope() and wep:GetValue("ScopeOverlay") then
s = s + math.Clamp(1 - diff:Length() / 4096, 0, 1) ^ 1.2 * wep:GetSightAmount() * dot * 3000 * math.Rand(0.95, 1.05)
end
if tr.Fraction == 1 then
s = TacRP.SS(s)
local toscreen = pos:ToScreen()
cam.Start2D()
surface.SetMaterial(flaremat)
surface.SetDrawColor(255, 255, 255, 255)
surface.DrawTexturedRect(toscreen.x - s / 2, toscreen.y - s / 2, s, s)
cam.End2D()
end
end
local rad = math.Rand(0.9, 1.1) * 128 * strength
local a = 50 + strength * 205
pos = pos + ang:Forward() * 2
pos = pos + diff:GetNormalized() * (2 + 14 * strength)
render.SetMaterial(flaremat)
render.DrawSprite(pos, rad, rad, Color(255, 255, 255, a))
end
function SWEP:DrawFlashlightGlares()
if !self:GetOwner():IsPlayer() then return end
for i, k in pairs(self.Attachments) do
if !k.Installed then continue end
local atttbl = TacRP.GetAttTable(k.Installed)
local src, dir
if atttbl.Blinding and self:GetTactical() then
if IsValid(k.WModel) then
src, dir = k.WModel:GetPos(), self:GetShootDir()
else
src, dir = self:GetTracerOrigin(), self:GetShootDir()
end
else
continue
end
local power = 1
local dot = -dir:Forward():Dot(EyeAngles():Forward())
local dot2 = dir:Forward():Dot((EyePos() - src):GetNormalized())
dot = (dot + dot2) / 2
if dot < 0 then continue end
power = power * math.Clamp(dot * 2 - 1, 0, 1)
local distsqr = (src - EyePos()):LengthSqr()
power = power * ((1 - math.Clamp(distsqr / 4194304, 0, 1)) ^ 1.25)
self:DrawFlashlightGlare(src, dir, power, dot)
end
end
local glintmat = Material("effects/blueflare1")
local glintmat2 = Material("tacrp/scope_flare")
function SWEP:DoScopeGlint()
--if self:GetOwner() == LocalPlayer() then return end
if !TacRP.ConVars["glint"]:GetBool() then return end
if !self:GetValue("ScopeOverlay") then return end
local src, dir = self:GetTracerOrigin(), self:GetShootDir()
local diff = EyePos() - src
local dot = -dir:Forward():Dot(EyeAngles():Forward())
local dot2 = dir:Forward():Dot(diff:GetNormalized())
dot = math.max(0, (dot + dot2) / 2) ^ 1.5
local strength = dot * math.Clamp((diff:Length() - 1024) / 3072, 0, 3) * math.Clamp(90 / self:GetValue("ScopeFOV") / 10, 0, 1)
local rad = strength * 128 * (self:GetSightAmount() * 0.5 + 0.5)
src = src + dir:Up() * 4 + diff:GetNormalized() * math.Clamp(diff:Length() / 2048, 0, 1) * 16
local a = math.min(255, strength * 200 + 100)
render.SetMaterial(glintmat)
render.DrawSprite(src, rad, rad, Color(a, a, a))
-- if self:GetSightAmount() > 0 then
render.SetMaterial(glintmat2)
render.DrawSprite(src, rad * 2, rad * 2, color_white)
-- end
end
function SWEP:DoMuzzleLight()
if (!IsFirstTimePredicted() and !game.SinglePlayer()) or !TacRP.ConVars["muzzlelight"]:GetBool() then return end
if IsValid(self.MuzzleLight) then self.MuzzleLight:Remove() end
local lamp = ProjectedTexture()
lamp:SetTexture("tacrp/muzzleflash_light")
local val1, val2
if self:GetValue("Silencer") then
val1, val2 = math.Rand(0.2, 0.4), math.Rand(100, 105)
lamp:SetBrightness(val1)
lamp:SetFOV(val2)
else
val1, val2 = math.Rand(2, 3), math.Rand(115, 120)
lamp:SetBrightness(val1)
lamp:SetFOV(val2)
end
lamp:SetFarZ(600)
lamp:SetPos(self:GetMuzzleOrigin() + self:GetShootDir():Forward() * 8)
lamp:SetAngles(self:GetShootDir() + Angle(math.Rand(-1, 1), math.Rand(-1, 1), math.Rand(0, 360)))
lamp:Update()
self.MuzzleLight = lamp
self.MuzzleLightStart = UnPredictedCurTime()
self.MuzzleLightEnd = UnPredictedCurTime() + 0.06
self.MuzzleLightBrightness = val1
self.MuzzleLightFOV = val2
-- In multiplayer the timer will last longer than intended - sh_think should kill the light first.
-- This is a failsafe for when the weapon stops thinking before light is killed (holstered, removed etc.).
timer.Simple(0.06, function()
if IsValid(lamp) then lamp:Remove() end
end)
end

View File

@@ -0,0 +1,106 @@
SWEP.VModel = nil
SWEP.WModel = nil
function SWEP:KillModel()
for _, model in pairs(self.VModel or {}) do
SafeRemoveEntity(model)
end
for _, model in pairs(self.WModel or {}) do
SafeRemoveEntity(model)
end
self.VModel = nil
self.WModel = nil
end
function SWEP:CreateAttachmentModel(wm, atttbl, slot, slottbl, custom_wm)
local model = atttbl.Model
if wm and atttbl.WorldModel then
model = atttbl.WorldModel
end
local csmodel = ClientsideModel(model)
if !IsValid(csmodel) then return end
csmodel.Slot = slot
local scale = Matrix()
local vec = Vector(1, 1, 1) * (atttbl.Scale or 1)
if wm then
vec = vec * (slottbl.WMScale or 1)
else
vec = vec * (slottbl.VMScale or 1)
end
scale:Scale(vec)
csmodel:EnableMatrix("RenderMultiply", scale)
csmodel:SetNoDraw(true)
local tbl = {
Model = csmodel,
Weapon = self
}
table.insert(TacRP.CSModelPile, tbl)
if wm then
table.insert(self.WModel, csmodel)
else
table.insert(self.VModel, csmodel)
end
return csmodel
end
function SWEP:SetupModel(wm, custom_wm)
self:KillModel()
if !wm and !IsValid(self:GetOwner()) then return end
if !wm then
self.VModel = {}
else
self.WModel = {}
end
if !wm and self:GetOwner() != LocalPlayer() and self:GetOwner() != LocalPlayer():GetObserverTarget() then return end
self:DoBodygroups(wm)
for slot, slottbl in pairs(self.Attachments) do
if !slottbl.Installed then continue end
local atttbl = TacRP.GetAttTable(slottbl.Installed)
if !atttbl.Model then continue end
local csmodel = self:CreateAttachmentModel(wm, atttbl, slot, slottbl)
csmodel.IsHolosight = atttbl.Holosight
if atttbl.Silencer then
local slmodel = self:CreateAttachmentModel(wm, atttbl, slot, slottbl)
slmodel.IsMuzzleDevice = true
slmodel.NoDraw = true
end
if wm then
slottbl.WModel = csmodel
else
slottbl.VModel = csmodel
end
end
if !wm then
self:CreateFlashlights()
local mat = self:GetValue("Material")
if mat then
local vm = self:GetOwner():GetViewModel()
vm:SetMaterial(mat)
end
end
end

View File

@@ -0,0 +1,37 @@
function SWEP:ReceiveWeapon(ids)
for slot, slottbl in pairs(self.Attachments) do
local attid = ids and ids[slot] or net.ReadUInt(TacRP.Attachments_Bits)
if attid == 0 then
slottbl.Installed = nil
else
slottbl.Installed = TacRP.Attachments_Index[attid]
end
end
self:InvalidateCache()
self:SetupModel(true)
self:SetupModel(false)
self.CertainAboutAtts = true
end
function SWEP:UpdateHolster()
local ply = self:GetOwner()
if IsValid(ply) and ply:IsPlayer() and ply:GetActiveWeapon() != self then
local visible = self:GetValue("HolsterVisible")
local slot = self:GetValue("HolsterSlot")
if visible and slot then
ply.TacRP_Holster = ply.TacRP_Holster or {}
ply.TacRP_Holster[slot] = self
end
end
end
function SWEP:RequestWeapon()
net.Start("tacrp_networkweapon")
net.WriteEntity(self)
net.SendToServer()
end

View File

@@ -0,0 +1,81 @@
function SWEP:SavePreset(filename)
if LocalPlayer() != self:GetOwner() then return end
filename = filename or "autosave"
local str = ""
for i, k in pairs(self.Attachments) do
if k.Installed then
str = str .. k.Installed
end
str = str .. "\n"
end
filename = TacRP.PresetPath .. self:GetClass() .. "/" .. filename .. ".txt"
file.CreateDir(TacRP.PresetPath .. self:GetClass())
file.Write(filename, str)
end
function SWEP:LoadPreset(filename)
if LocalPlayer() != self:GetOwner() then return end
filename = TacRP.PresetPath .. self:GetClass() .. "/" .. "autosave" .. ".txt"
if !file.Exists(filename, "DATA") then return end
local f = file.Open(filename, "r", "DATA")
if !f then return end
local presetTbl = {}
for i = 1, table.Count(self.Attachments) do
local line = f:ReadLine()
if !line then continue end
presetTbl[i] = string.Trim(line, "\n")
end
local anyinstalled = false
for i = 1, table.Count(self.Attachments) do
if !self.Attachments[i] then continue end
local att = presetTbl[i]
if att == "" then
self.Attachments[i].Installed = nil
continue
end
if att == self.Attachments[i].Installed then continue end
if !TacRP.GetAttTable(att) then continue end
self.Attachments[i].Installed = att
anyinstalled = true
end
f:Close()
if !anyinstalled then return end
net.Start("TacRP_receivepreset")
net.WriteEntity(self)
for i, k in pairs(self.Attachments) do
if !k.Installed then
net.WriteUInt(0, TacRP.Attachments_Bits)
else
local atttbl = TacRP.GetAttTable(k.Installed)
net.WriteUInt(atttbl.ID or 0, TacRP.Attachments_Bits)
end
end
net.SendToServer()
self:SetupModel(false)
self:SetupModel(true)
self:InvalidateCache()
self:SetBaseSettings()
end

View File

@@ -0,0 +1,993 @@
local function filledcircle(x, y, radius, seg)
local cir = {}
table.insert(cir, {
x = x,
y = y,
u = 0.5,
v = 0.5
})
for i = 0, seg do
local a = math.rad((i / seg) * -360)
table.insert(cir, {
x = x + math.sin(a) * radius,
y = y + math.cos(a) * radius,
u = math.sin(a) / 2 + 0.5,
v = math.cos(a) / 2 + 0.5
})
end
local a = math.rad(0)
table.insert(cir, {
x = x + math.sin(a) * radius,
y = y + math.cos(a) * radius,
u = math.sin(a) / 2 + 0.5,
v = math.cos(a) / 2 + 0.5
})
surface.DrawPoly(cir)
end
local function slicedcircle(x, y, radius, seg, ang0, ang1)
local cir = {}
ang0 = ang0 + 90
ang1 = ang1 + 90
local arcseg = math.Round(360 / math.abs(ang1 - ang0) * seg)
table.insert(cir, {
x = x,
y = y,
u = 0.5,
v = 0.5
})
for i = 0, arcseg do
local a = math.rad((i / arcseg) * -math.abs(ang1 - ang0) + ang0)
table.insert(cir, {
x = x + math.sin(a) * radius,
y = y + math.cos(a) * radius,
u = math.sin(a) / 2 + 0.5,
v = math.cos(a) / 2 + 0.5
})
end
surface.DrawPoly(cir)
end
SWEP.GrenadeMenuAlpha = 0
SWEP.BlindFireMenuAlpha = 0
TacRP.CursorEnabled = false
local currentnade
local currentind
local lastmenu
function SWEP:DrawGrenadeHUD()
if !TacRP.ConVars["nademenu"]:GetBool() then return end
if !self:IsQuickNadeAllowed() then return end
-- adapted from tfa vox radial menu
local nades = self:GetAvailableGrenades(false)
local scrw = ScrW()
local scrh = ScrH()
local r = TacRP.SS(128)
local r2 = TacRP.SS(40)
local sg = TacRP.SS(32)
local ri = r * 0.667
local arcdegrees = 360 / math.max(1, #nades)
local d = 360
local ft = FrameTime()
local cursorx, cursory = input.GetCursorPos()
local mouseangle = math.deg(math.atan2(cursorx - scrw / 2, cursory - scrh / 2))
local mousedist = math.sqrt(math.pow(cursorx - scrw / 2, 2) + math.pow(cursory - scrh / 2, 2))
mouseangle = math.NormalizeAngle(360 - (mouseangle - 90) + arcdegrees)
if mouseangle < 0 then
mouseangle = mouseangle + 360
end
local iskeydown = self:GetOwner():KeyDown(self.GrenadeMenuKey)
if self.GrenadeMenuKey == IN_GRENADE1 and !input.LookupBinding("+grenade1") then
iskeydown = input.IsKeyDown(TacRP.GRENADE1_Backup)
elseif self.GrenadeMenuKey == IN_GRENADE2 and !input.LookupBinding("+grenade2") then
iskeydown = input.IsKeyDown(TacRP.GRENADE2_Backup)
end
if iskeydown and !self:GetPrimedGrenade() and self.BlindFireMenuAlpha == 0 and self:GetHolsterTime() == 0 then
self.GrenadeMenuAlpha = math.Approach(self.GrenadeMenuAlpha, 1, 15 * ft)
if !lastmenu then
gui.EnableScreenClicker(true)
TacRP.CursorEnabled = true
lastmenu = true
end
if mousedist > r2 then
local i = math.floor( mouseangle / arcdegrees ) + 1
currentnade = nades[i]
currentind = i
else
currentnade = self:GetGrenade()
currentind = nil
end
self.GrenadeMenuHighlighted = currentind
else
self.GrenadeMenuAlpha = math.Approach(self.GrenadeMenuAlpha, 0, -10 * ft)
if lastmenu then
if !self:GetCustomize() then
gui.EnableScreenClicker(false)
TacRP.CursorEnabled = false
end
if currentnade then
if currentnade.Index != self:GetGrenade().Index then
self:GetOwner():EmitSound("tacrp/weapons/grenade/roll-" .. math.random(1, 3) .. ".wav")
end
net.Start("tacrp_togglenade")
net.WriteUInt(currentnade.Index, 4)
net.WriteBool(false)
net.SendToServer()
self.Secondary.Ammo = currentnade.Ammo or "none"
end
lastmenu = false
end
end
if self.GrenadeMenuAlpha <= 0 then
return
end
local a = self.GrenadeMenuAlpha
local col = Color(255, 255, 255, 255 * a)
surface.DrawCircle(scrw / 2, scrh / 2, r, 255, 255, 255, a * 255)
surface.SetDrawColor(0, 0, 0, a * 200)
draw.NoTexture()
filledcircle(scrw / 2, scrh / 2, r, 32)
if #nades == 0 then
local nadetext = TacRP:GetPhrase("hint.nogrenades")
surface.SetFont("TacRP_HD44780A00_5x8_8")
local nadetextw = surface.GetTextSize(nadetext)
surface.SetTextPos(scrw / 2 - nadetextw * 0.5, scrh / 2 + TacRP.SS(6))
surface.DrawText(nadetext)
return
end
surface.SetDrawColor(150, 150, 150, a * 100)
draw.NoTexture()
if currentind then
local i = currentind
local d0 = 0 - arcdegrees * (i - 2)
slicedcircle(scrw / 2, scrh / 2, r, 32, d0, d0 + arcdegrees)
else
filledcircle(scrw / 2, scrh / 2, r2, 32)
end
surface.SetDrawColor(0, 0, 0, a * 255)
surface.DrawCircle(scrw / 2, scrh / 2, r2, 255, 255, 255, a * 255)
for i = 1, #nades do
local rad = math.rad( d + arcdegrees * 0.5 )
surface.SetDrawColor(255, 255, 255, a * 255)
surface.DrawLine(
scrw / 2 + math.cos(math.rad(d)) * r2,
scrh / 2 - math.sin(math.rad(d)) * r2,
scrw / 2 + math.cos(math.rad(d)) * r,
scrh / 2 - math.sin(math.rad(d)) * r)
local nadex, nadey = scrw / 2 + math.cos(rad) * ri, scrh / 2 - math.sin(rad) * ri
local nade = nades[i]
local qty = nil --"INF"
if nade.Singleton then
qty = self:GetOwner():HasWeapon(nade.GrenadeWep) and 1 or 0
elseif !TacRP.IsGrenadeInfiniteAmmo(nade.Index) then
qty = self:GetOwner():GetAmmoCount(nade.Ammo)
end
if !qty or qty > 0 then
surface.SetDrawColor(255, 255, 255, a * 255)
surface.SetTextColor(255, 255, 255, a * 255)
else
surface.SetDrawColor(175, 175, 175, a * 255)
surface.SetTextColor(175, 175, 175, a * 255)
end
if nade.Icon then
surface.SetMaterial(nade.Icon)
surface.DrawTexturedRect(nadex - sg * 0.5, nadey - sg * 0.5 - TacRP.SS(8), sg, sg)
end
local nadetext = TacRP:GetPhrase("quicknade." .. nade.PrintName .. ".name") or nade.PrintName
surface.SetFont("TacRP_HD44780A00_5x8_8")
local nadetextw = surface.GetTextSize(nadetext)
surface.SetTextPos(nadex - nadetextw * 0.5, nadey + TacRP.SS(6))
surface.DrawText(nadetext)
if !TacRP.IsGrenadeInfiniteAmmo(nade.Index) then
local qty
if nade.Singleton then
qty = self:GetOwner():HasWeapon(nade.GrenadeWep) and "x1" or "x0"
else
qty = "x" .. tostring(self:GetOwner():GetAmmoCount(nade.Ammo))
end
local qtyw = surface.GetTextSize(qty)
surface.SetTextPos(nadex - qtyw * 0.5, nadey + TacRP.SS(15))
surface.DrawText(qty)
end
d = d - arcdegrees
end
local nade = currentnade
if nade.Icon then
surface.SetMaterial(nade.Icon)
surface.SetDrawColor(255, 255, 255, a * 255)
surface.DrawTexturedRect(scrw / 2 - sg * 0.5, scrh / 2 - sg * 0.5 - TacRP.SS(8), sg, sg)
end
local nadetext = TacRP:GetPhrase("quicknade." .. nade.PrintName .. ".name") or nade.PrintName
surface.SetFont("TacRP_HD44780A00_5x8_8")
local nadetextw = surface.GetTextSize(nadetext)
surface.SetTextPos(scrw / 2 - nadetextw * 0.5, scrh / 2 + TacRP.SS(6))
surface.SetTextColor(255, 255, 255, a * 255)
surface.DrawText(nadetext)
if !TacRP.IsGrenadeInfiniteAmmo(nade.Index) then
local qty
if nade.Singleton then
qty = self:GetOwner():HasWeapon(nade.GrenadeWep) and "x1" or "x0"
else
qty = "x" .. tostring(self:GetOwner():GetAmmoCount(nade.Ammo))
end
surface.SetFont("TacRP_HD44780A00_5x8_8")
local qtyw = surface.GetTextSize(qty)
surface.SetTextPos(scrw / 2 - qtyw * 0.5, scrh / 2 + TacRP.SS(16))
surface.SetTextColor(255, 255, 255, a * 255)
surface.DrawText(qty)
end
-- description box is blocked in customize
if self:GetCustomize() then return end
local w, h = TacRP.SS(96), TacRP.SS(128)
local tx, ty = scrw / 2 + r + TacRP.SS(16), scrh / 2
-- full name
surface.SetDrawColor(0, 0, 0, 200 * a)
TacRP.DrawCorneredBox(tx, ty - h * 0.5 - TacRP.SS(28), w, TacRP.SS(24), col)
surface.SetTextColor(255, 255, 255, a * 255)
local name = TacRP:GetPhrase("quicknade." .. nade.PrintName .. ".name.full")
or TacRP:GetPhrase("quicknade." .. nade.PrintName .. ".name")
or nade.FullName
or nade.PrintName
surface.SetFont("TacRP_Myriad_Pro_16")
local name_w, name_h = surface.GetTextSize(name)
if name_w > w then
surface.SetFont("TacRP_Myriad_Pro_14")
name_w, name_h = surface.GetTextSize(name)
end
surface.SetTextPos(tx + w / 2 - name_w / 2, ty - h * 0.5 - TacRP.SS(28) + TacRP.SS(12) - name_h / 2)
surface.DrawText(name)
-- Description
surface.SetDrawColor(0, 0, 0, 200 * a)
TacRP.DrawCorneredBox(tx, ty - h * 0.5, w, h, col)
surface.SetFont("TacRP_Myriad_Pro_8")
surface.SetTextPos(tx + TacRP.SS(4), ty - h / 2 + TacRP.SS(2))
surface.DrawText( TacRP:GetPhrase("quicknade.fuse") )
surface.SetFont("TacRP_Myriad_Pro_8")
surface.SetTextPos(tx + TacRP.SS(4), ty - h / 2 + TacRP.SS(10))
surface.DrawText(TacRP:GetPhrase("quicknade." .. nade.PrintName .. ".dettype") or nade.DetType or "")
surface.SetFont("TacRP_Myriad_Pro_8")
surface.SetTextPos(tx + TacRP.SS(4), ty - h / 2 + TacRP.SS(22))
surface.DrawText( TacRP:GetPhrase("cust.description") )
surface.SetFont("TacRP_Myriad_Pro_8")
if nade.Description then
nade.DescriptionMultiLine = TacRP.MultiLineText(TacRP:GetPhrase("quicknade." .. nade.PrintName .. ".desc") or nade.Description or "", w - TacRP.SS(7), "TacRP_Myriad_Pro_8")
end
surface.SetTextColor(255, 255, 255, a * 255)
for i, text in ipairs(nade.DescriptionMultiLine) do
surface.SetTextPos(tx + TacRP.SS(4), ty - h / 2 + TacRP.SS(30) + (i - 1) * TacRP.SS(8))
surface.DrawText(text)
end
surface.SetFont("TacRP_Myriad_Pro_8")
surface.SetDrawColor(0, 0, 0, 200 * a)
-- Only use the old bind hints if current hint is disabled
if TacRP.ConVars["hints"]:GetBool() then
self.LastHintLife = CurTime()
return
end
if TacRP.ConVars["nademenu_click"]:GetBool() then
local binded = input.LookupBinding("grenade1")
TacRP.DrawCorneredBox(tx, ty + h * 0.5 + TacRP.SS(2), w, TacRP.SS(28), col)
surface.SetTextPos(tx + TacRP.SS(4), ty + h / 2 + TacRP.SS(4))
surface.DrawText( "[ " .. TacRP.GetBind("+attack") .. " ] " .. TacRP:GetPhrase("hint.quicknade.over") )
surface.SetTextPos(tx + TacRP.SS(4), ty + h / 2 + TacRP.SS(12))
surface.DrawText( "[ " .. TacRP.GetBind("+attack2") .. " ] " .. TacRP:GetPhrase("hint.quicknade.under") )
if TacRP.AreTheGrenadeAnimsReadyYet then
surface.SetTextPos(tx + TacRP.SS(4), ty + h / 2 + TacRP.SS(20))
surface.DrawText( "[ MOUSE3 ] " .. TacRP:GetPhrase("hint.quicknade.pull_out") )
end
else
local binded = input.LookupBinding("grenade1")
if binded then button = TacRP.GetBind("grenade1") else button = "G" end
TacRP.DrawCorneredBox(tx, ty + h * 0.5 + TacRP.SS(2), w, TacRP.SS(28), col)
surface.SetTextPos(tx + TacRP.SS(4), ty + h / 2 + TacRP.SS(4))
surface.DrawText("[ " ..button .. " ] " .. TacRP:GetPhrase("hint.quicknade.over") .. " " .. TacRP:GetPhrase("hint.hold") )
surface.SetTextPos(tx + TacRP.SS(4), ty + h / 2 + TacRP.SS(12))
surface.DrawText("[ " .. button .. " ] " .. TacRP:GetPhrase("hint.quicknade.under") )
if TacRP.AreTheGrenadeAnimsReadyYet then
surface.SetTextPos(tx + TacRP.SS(4), ty + h / 2 + TacRP.SS(20))
surface.DrawText( "[ MOUSE3 ] " .. TacRP:GetPhrase("hint.quicknade.pull_out") )
end
end
end
local mat_none = Material("tacrp/blindfire/none.png", "smooth")
local mat_wall = Material("tacrp/blindfire/wall.png", "smooth")
local bf_slices = {
{TacRP.BLINDFIRE_RIGHT, mat_wall, 270},
{TacRP.BLINDFIRE_KYS, Material("tacrp/blindfire/suicide.png", "smooth"), 0},
{TacRP.BLINDFIRE_LEFT, mat_wall, 90},
{TacRP.BLINDFIRE_UP, mat_wall, 0},
}
local bf_slices2 = {
{TacRP.BLINDFIRE_RIGHT, mat_wall, 270},
{TacRP.BLINDFIRE_LEFT, mat_wall, 90},
{TacRP.BLINDFIRE_UP, mat_wall, 0},
}
local bf_slices3 = {
{TacRP.BLINDFIRE_RIGHT, mat_wall, 270},
{TacRP.BLINDFIRE_NONE, mat_none, 0},
{TacRP.BLINDFIRE_LEFT, mat_wall, 90},
{TacRP.BLINDFIRE_UP, mat_wall, 0},
}
local lastmenu_bf
local bf_suicidelock
local bf_funnyline
local bf_lines = {
"Go ahead, see if I care.",
"Why not just killbind?",
"But you have so much to live for!",
"Just like Hemingway.",
"... NOW!",
"DO IT!",
"Now THIS is realism.",
"See you in the next life!",
"Time to commit a little insurance fraud.",
"Don't give them the satisfaction.",
"Why not jump off a building instead?",
"Ripperoni in pepperoni.",
"F",
"L + ratio + you're a minge + touch grass",
"You serve NO PURPOSE!",
"type unbindall in console",
"Citizens aren't supposed to have guns.",
"I have decided that I want to die.",
"What's the point?",
"eh",
"not worth",
"Just like Hitler.",
"Kill your own worst enemy.",
"You've come to the right place.",
"Don't forget to like and subscribe",
"noooooooooooooo",
"tfa base sucks lololololol",
"The HUD is mandatory.",
"No Bitches?",
"now you have truly become garry's mod",
"type 'tacrp_rock_funny 1' in console",
"is only gaem, y u haev to be mad?",
"And so it ends.",
"Suicide is badass!",
"Stop staring at me and get to it!",
"you like kissing boys don't you",
"A most tactical decision.",
"Bye have a great time!",
"Try doing this with the Dual MTX!",
"Try doing this with the RPG-7!",
"sad",
"commit sudoku",
"kermit suicide",
"You can disable this button in the options.",
"Goodbye, cruel world!",
"Adios!",
"Sayonara, [------]!",
"Nice boat!",
"I find it quite Inconceievable!",
"Delete system32.dll",
"Press ALT+F4 for admin gun",
"AKA: Canadian Medkit",
"The coward's way out",
"No man lives forever.",
"Goodbye, cruel world.",
"Doing this will result in an admin sit",
"Do it, before you turn.",
"Your HUD Buddy will miss you.",
"1-800-273-8255: Suicide and Crisis Support",
"Guaranteed dead or your money back!",
"Free health restore",
"For best results, make a scene in public",
"What are you, chicken?",
"Don't pussy out NOW",
"-1 Kill",
"You COULD type 'kill' in console",
"You know, back before all this started, me and my buddy Keith would grab a couple of .25s, piss tiny little guns, and take turns down by the river shootin' each other in the forehead with 'em. Hurt like a motherfucker, but we figured if we kept going, we could work our way up to bigger rounds, and eventually, ain't nothin' gon' be able to hurt us no more. Then we moved up to .22 and... well, let's just say I didn't go first.",
"How many headshots can YOU survive?",
"Shoot yourself in the head CHALLENGE",
"The only remedy to admin abuse",
"Try doing this with the Riot Shield!",
"Too bad you can't overcook nades",
"It's incredible you can survive this",
"Physics-based suicide",
"Sheep go to Heaven; goats go to Hell.",
"Nobody will be impressed.",
"You have a REALLY tough skull",
"Think about the clean-up",
"Canadian Healthcare Edition",
"A permanent solution to a temporary problem.",
"At least take some cops with you",
"Don't let them take you alive!",
"Teleport to spawn!",
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA",
"THE VOICES TOLD ME TO DO IT",
"Equestria awaits.",
"Truck-Kun sends you to Heaven. Gun-San sends you to Hell.",
"40,000 men and women everyday",
"And it's all YOUR fault!",
"YOU made me do this!",
"AAA quality game design",
"Stream it on TikTok!",
"This button is banned in Russia",
"Was it ethical to add this? No. But it was funny.",
"Wrote amazing eulogy, couldn't wait for funeral",
"It's gonna be a closed casket for you I think",
"A shitpost in addon form",
"More fun than working on ARC9",
"A final rebellion against an indifferent world.",
"Probably part of an infinite money exploit",
"You're not a real gamer until you've done this",
"We call this one the Detroit Cellphone",
"Do a backflip!",
"Do it for the Vine",
"Show it to your mother",
"To kill for yourself is murder. To kill yourself is hilarious.",
"This is all your fault.",
"Life begins at the other side of despair.",
"You are still a good person.",
"Reports of my survival have been greatly exaggerated.",
"Home? We can't go home.",
"No matter what happens next, don't be too hard on yourself.",
"There is no escape.",
"Is this really what you want, Walker? So be it.",
"We call this one the Devil's Haircut",
"Open your mind",
"Edgy jokes for dumbass teens",
"The fun will be endless",
"The living will envy the dead",
"There is only darkness.",
"There is nothing on the other side.",
"Is this how you get your kicks?",
"ngl this is how I feel when I log on to a server and see m9k",
"Administer straight to forehead",
"No tactical advantages whatsoever.",
"The best is yet to come",
"I know what you did, Mikey.",
"AMONG US AMONG US AMONG US AMONG US AMONG US AMONG US AMONG US AMONG US AMONG US AMONG US AMONG US AMONG US",
"What would your waifu think?",
"You won't get to see her, you know.",
"ez",
"Ehh... it's ez",
"So ez it's hard to believe",
"As shrimple as that",
"Well, I won't try and stop you",
"Send it to your favorite Youtubers",
"SHED YOUR BODY FREE YOUR SOUL",
"Suicide is illegal because you're damaging government property.",
"ESCAPE THE SIMULATION",
"Classic schizoposting",
"See you in Hell",
"The person you are most likely to kill is yourself.",
"There will be no encore.",
"Can't you pick a less messy method?",
"Just like Jeffrey Epstein... *snort*",
"The enemy. Shoot the enemy.",
"Let's see you do this on M9K",
"You won't do it, you pussy.",
"Ka-POW!",
"Bam-kerchow!",
"Zoop!",
"Zycie jest bez sensu i wszyscy zginemy",
"We really shouldn't be encouraging this.",
"You'll never see all the quotes",
"When the going gets tough, the tough get going",
"Acute cerebral lead poisoning",
"Those bullets are laced with estrogen, you know",
"google en passant",
"And then he sacrificed... THE PLAYERRRRRRRRRRR",
"You should grow and change as a person",
"dont leave me </3",
"Nyoooom~",
"yeah take that fat L",
"not very ez now is it",
"You'll never live to see the day TF2 gets updated.",
"go commit die",
"oof",
"早死早超生",
"-800 social credit 干得好",
"So long, and thanks for all the tactical realism!",
"THE END IS NEVER THE END IS NEVER THE END IS NEVER THE END IS NEVER THE END IS NEVER THE END IS NEVER THE END IS NEVER THE END IS NEVER THE END IS NEVER THE END IS NEVER",
"Dying a virgin?",
"Error: Quip not found.",
"Do it, I dare you.",
"If you're reading this, they trapped me at the quip factory and they're forcing me to write these. Please send help.",
"I'm not locked in here with you. You're locked in here with me.",
"Only one bullet left. Not for the enemy.",
"Preferable to surrender.",
"Such a beautiful death.",
"See you later. Wait, actually...",
"You're not going to like what happens next.",
"Remember that you are loved.",
"Whoever retreats, I'll shoot. If someone gets injured, there will be no rescue. I'll just finish him off.",
"I'm not going to die. I'm going to find out if I'm really alive.",
"Have a nice life.",
"One less murderer.",
"There is no evidence showing that Russian Roulette was ever actually played in Russia.",
"Don't you have anything better to do?",
"Pre-order a video game, so you'll live to see it release.",
"Sorry, I just don't feel like it today.",
"No, please. Don't.",
"Blind fire backwards",
"At least you can't miss",
"And for my final magic trick...",
"Take your own life, so they won't take it from you.",
"Never point a gun at anything you aren't willing to destroy.",
"Lower the gun! No, higher... there, that's the cerebellum.",
"It'll hurt, but only for a moment.",
"Goodness, imagine if you survive.",
"Such a waste of life.",
"None of it meant anything to me.",
"Escape the Matrix.",
"Death shall be a great adventure.",
"Give me liberty, or give me death.",
"I never wanted to grow old anyway.",
"All debts must be repaid.",
"Eros and Thanatos.",
"Adults only.",
"You must be 18 or above to click this button.",
"Hey, what's up guys? It's your boy, back again for another EPIC Garry's Mod video.",
"That's just crazy, man. For real.",
"This is the only way to free your soul.",
"Hey, come on, we can talk about this.",
"One day you're alive, the next...",
"But... why?",
"Lived as he died; a virgin.",
"A very stupid decision.",
"I'm not going to tell you what to do, but...",
"You should do it.",
"You're not going to do it, are you?",
"Are you really just going to sit here and read all these quotes?",
"Et tu, Brutus?",
"We didn't like you anyway.",
"You're not going to get away with this.",
"You'll just respawn anyway.",
"How do you know you're the same person you were yesterday?",
"Scratch the itch at the back of your head.",
"You're not going to get a second chance.",
"Think of how much they'll miss you.",
"They'll be sorry. They'll be REAL sorry.",
"The train leaves the station every evening, 21:00.",
"Put your finger on the eject button, see how alive it makes you feel.",
"It's okay to kill yourself.",
"I'm gonna blow my brains out. Gonna close this one final case and then *blam* -- I'm outta here.",
"Looks like the circus left town, but the clowns are still here.",
"Establish your authority.",
"Everybody calm down! This is only a demonstration!",
"What in the name of fuck are you doing?",
"I want to see where this is going.",
"Be careful -- it's loaded.",
"It tastes like iron and hell.",
"These are my thoughts. This is my head.",
"You will NEVER forget what happens in five seconds!",
"Inside the small mechanism, you can hear a spring tensing up.",
"There's this itch in the middle of your skull, where you've never reached. Never scratched...",
"He's not gonna off himself, c'mon!",
"Go ahead. Three, two...",
"We can't have any fun if you kill yourself.",
"I... don't know why she left you. You can still turn this around, come on.",
"When the FISH is FUNNY",
"A dog walked into a tavern and said, \"I can't see a thing. I'll open this one.\"",
"This is how the revolution starts.",
"Oh what fun it is to die on a one horse open sleigh",
"But... I love you!",
"Even now, the evil seed of what you have done germinates within you.",
"How cliche.",
"Oh, you can do better than THAT.",
"Become an hero.",
"A tragedy of the highest order.",
"What if you were the impostor all along?",
"Sorry. For everything.",
"I'm sorry I couldn't do more for you.",
"See you soon.",
"Say hi to the Devil for me.",
"The punishment for suicide is eternal damnation.",
"You can't walk back from this one.",
"This one is a blank; I just know it.",
"Try shooting the other guy instead.",
"God, are you watching?",
"The moment of truth.",
"Sponsored by Donghua Jinlong Glycine Chemical Co. LTD",
"Don't try this one at home.",
"Redecorate.",
"The Kurt Cobain haircut.",
"The closest thing to love you'll get to experience.",
"Wait! Before you die - subscribe to my other mods.",
"Yeah, you could say I have a dark sense of humor",
"That's all, folks.",
"Farewell and goodbye.",
"We hope you enjoyed your time with us tonight.",
"Show them who's boss. Go on.",
"This is actually what happened to that Boeing guy",
"You're making a big mistake.",
"The bullets enter the chamber in an unknown order.",
"Kill yourself, or die trying.",
"No. This is wrong.",
"But- you can't!",
"All the effort in the world would have gone to waste. Until- well. Let's just say your hour has... come again.",
"Become a Liveleak star.",
"Cha-cha real smooth.",
"The only way to defeat Them.",
"Ashes to ashes.",
"Death speedrun",
"You were gonna die eventually.",
"'Cuz everybody's gotta die sometime.", -- a little piece of heaven, avenged sevenfold
"I've made the change; I won't see you tonight.", -- i won't see you tonight pt. 1, avenged sevenfold
"No more breath inside; essence left my heart tonight.", -- i won't see you tonight pt. 1, avenged sevenfold
"I know this can't be right, stuck in a dream, a nightmare full of sorrow.", -- i won't see you tonight pt. 2, avenged sevenfold
"I was me, but now he's gone.", -- fade to black, metallica
"Death greets me warm, now I will just say goodbye.", -- fade to black, metallica
"I have to laugh out loud; I wish I didn't like this.", -- wait and bleed, slipknot
"Lay away a place for me, 'cuz as soon as I'm done, I'll be on my way to live eternally.", -- so far away, avenged sevenfold
"Now, I think I understand how this world can overcome a man.", -- fiction, avenged sevenfold
"Heard there's peace just on the other side.", -- fiction, avenged sevenfold
"I hope you find your own way when I'm not with you tonight.", -- fiction, avenged sevenfold
"A truant finds home, and a wish to hold on.", -- immortality, pearl jam
"Makes much more sense to live in the present tense.", -- present tense, pearl jam
"Darkness comes in waves, tell me, why invite it to stay?", -- life wasted, pearl jam
"You flirt with suicide; sometimes, that's okay.", -- falling away from me, korn
"I flirt with suicide; sometimes, kill the pain.", -- falling away from me, korn
"Die, motherfucker, die!", -- creeping death, metallica
"How beautiful life is now, when my time has come.", -- life eternal, mayhem
"Can't really live, can't really endure.", -- everything ends, slipknot
"What the fuck was I thinking? Anybody want to tell me I'm fine?", -- everything ends, slipknot
-- Translated and abridged excerpts from Kamikaze pilots' manual
"Breathe deeply three times. Say in your mind: \"Yah\" (field), \"Kyu\" (ball), \"Joh\" (all right) as you breathe deeply.",
"Be always pure-hearted and cheerful. A loyal fighting man is a pure-hearted and filial son.",
"If you feel nervous, piss.",
"You have lived for 20 years or more. You must exert your full might for the last time in your life. Exert supernatural strength.",
"Every deity and the spirits of your dead comrades are watching you intently. They will tell you what fun they had.",
"You may nod then, or wonder what happened. You may even hear a final sound like the breaking of crystal. Then you are no more.",
-- Kamikaze manual ends
"How can you live with yourself?",
"A man never steps into the same river twice.",
"I don't blame you.",
"A robot must protect its own existence as long as such protection does not conflict with the First or Second Law.",
"Where is female_05?",
"See you in Hell.",
"I will not say 'Da svidanya', Commander, because I can assure you, we will never meet again.", -- Red Alert 3
"Die Krieg ist verlun.", -- Der Untergang :)
"You're a bad kid.",
"What would your mother think, if she could see you now?",
"I am the Law.",
"Fire and forget.",
"We will meet again, at the end of Days.",
"You're not gonna like where you go next.",
"Uh oh!!! The SERVERBLIGHT is coming!!!",
"Oh, what's the point.",
"Why even bother?",
"Cut my life into pieces; this is my last resort.", -- Last Resort by Papa Roach
"I wish somebody would tell me I'm fine.",
"It all started when I lost my mother.",
"I can't go on living this way.",
"Nothing's alright. Nothing is fine.", -- End Papa Roach
"Would it not be wondrous for this whole nation to be destroyed like a beautiful flower?",
"You are borderline retarded, ya fucking dipshit.",
"If we could talk, you would understand.",
"Think of the poorest person you know and see if your next act will be of any use to him.",
"Let your every day be full of joy, love the child that holds your hand, let your wife delight in your embrace, for these alone are the concerns of humanity.",
"I am the flail of God. If you had not committed great sins, God would not have sent a punishment like me upon you.",
"Against stupidity, the gods themselves contend in vain.",
"I believe today that my conduct is in accordance with the will of the Almighty.",
"Mein leben!",
"Don't wait until tomorrow to do what can be done today.",
"Oh, it's only 9mm. You'll be fine.",
"Uh, that's airsoft, right?",
"I can prove it wasn't murder! You see, first he did this-",
"What are you doing!? The safety's on!",
"Join me, and choose happiness.",
"Nothing you do has any effect on anything.",
"No one will remember your name when you die.",
"An eye for an eye.",
"But what do the quips mean, really?",
"Personally, I use TacRP for the quips.",
"Eh, register for organ donation first.",
"Don't forget to wash your foreskin!",
"There are fates worse than death.",
"This is pay to win.",
"This is the LIVING room! You can't do that here!",
"For god's sake, stop! Do it in the bathtub, it'll be easier to clean.",
"Upon closer inspection, he is merely pretending to be dead.",
"Resistance to tyranny is obedience to God.",
"Now's your chance to be a big shot.",
"Now or never.",
"I don't want to live forever.",
"It's my life.",
"I did it my way.",
"Might as well jump.",
"But you'll have to have them all pulled out after the Savoy Truffle.",
"What if your head just did that"
}
local function canhighlight(self, slice)
if !self:GetValue("CanBlindFire") and self:GetValue("CanSuicide") then return !slice or slice[1] == TacRP.BLINDFIRE_NONE or slice[1] == TacRP.BLINDFIRE_KYS end
return true
end
local lastseenfunnyline = false
local startseefunnylinetime = 0
function SWEP:DrawBlindFireHUD()
if !TacRP.ConVars["blindfiremenu"]:GetBool() then lastseenfunnyline = false return end
local nocenter = TacRP.ConVars["blindfiremenu_nocenter"]:GetBool()
local nosuicide = nocenter or TacRP.ConVars["idunwannadie"]:GetBool()
-- adapted from tfa vox radial menu
local ft = FrameTime()
local scrw = ScrW()
local scrh = ScrH()
local r = TacRP.SS(72)
local r2 = TacRP.SS(24)
local sg = TacRP.SS(32)
local ri = r * 0.667
local s = 45
local slices = bf_slices
if nocenter then
slices = bf_slices3
elseif nosuicide then
slices = bf_slices2
s = 90
end
if currentind and currentind > #slices then currentind = 0 end
local arcdegrees = 360 / #slices
local d = 360 - s
local cursorx, cursory = input.GetCursorPos()
local mouseangle = math.deg(math.atan2(cursorx - scrw / 2, cursory - scrh / 2))
local mousedist = math.sqrt(math.pow(cursorx - scrw / 2, 2) + math.pow(cursory - scrh / 2, 2))
if #slices == 3 then
mouseangle = math.NormalizeAngle(360 - mouseangle + arcdegrees) -- ???
else
mouseangle = math.NormalizeAngle(360 - (mouseangle - s) + arcdegrees)
end
if mouseangle < 0 then
mouseangle = mouseangle + 360
end
if (self:GetOwner():KeyDown(IN_ZOOM) or self:GetOwner().TacRPBlindFireDown) and self:CheckBlindFire(true) and self.GrenadeMenuAlpha == 0 then
self.BlindFireMenuAlpha = math.Approach(self.BlindFireMenuAlpha, 1, 15 * ft)
if !lastmenu_bf then
gui.EnableScreenClicker(true)
TacRP.CursorEnabled = true
lastmenu_bf = true
if self:GetBlindFireMode() == TacRP.BLINDFIRE_KYS then
bf_suicidelock = 0
else
bf_suicidelock = 1
bf_funnyline = nil
end
end
if mousedist > r2 then
local i = math.floor( mouseangle / arcdegrees ) + 1
currentind = i
else
currentind = 0
end
else
self.BlindFireMenuAlpha = math.Approach(self.BlindFireMenuAlpha, 0, -10 * ft)
if lastmenu_bf then
if !self:GetCustomize() then
gui.EnableScreenClicker(false)
TacRP.CursorEnabled = false
end
if (!nocenter or currentind > 0) and (nosuicide or bf_suicidelock == 0 or currentind != 2) then
net.Start("tacrp_toggleblindfire")
net.WriteUInt(currentind > 0 and slices[currentind][1] or TacRP.BLINDFIRE_NONE, TacRP.BlindFireNetBits)
net.SendToServer()
end
lastmenu_bf = false
end
end
if self.BlindFireMenuAlpha < 1 then
bf_funnyline = nil
lastseenfunnyline = false
end
if self.BlindFireMenuAlpha <= 0 then
return
end
local a = self.BlindFireMenuAlpha
local col = Color(255, 255, 255, 255 * a)
surface.DrawCircle(scrw / 2, scrh / 2, r, 255, 255, 255, a * 255)
surface.SetDrawColor(0, 0, 0, a * 200)
draw.NoTexture()
filledcircle(scrw / 2, scrh / 2, r, 32)
if currentind and canhighlight(self, slices[currentind]) then
surface.SetDrawColor(150, 150, 150, a * 100)
draw.NoTexture()
if currentind > 0 then
if !nosuicide and currentind == 2 and bf_suicidelock > 0 then
surface.SetDrawColor(150, 50, 50, a * 100)
end
local d0 = -s - arcdegrees * (currentind - 2)
slicedcircle(scrw / 2, scrh / 2, r, 32, d0, d0 + arcdegrees)
else
filledcircle(scrw / 2, scrh / 2, r2, 32)
end
end
surface.SetDrawColor(0, 0, 0, a * 255)
surface.DrawCircle(scrw / 2, scrh / 2, r2, 255, 255, 255, a * 255)
for i = 1, #slices do
local rad = math.rad( d + arcdegrees * 0.5 )
surface.SetDrawColor(255, 255, 255, a * 255)
surface.DrawLine(
scrw / 2 + math.cos(math.rad(d)) * r2,
scrh / 2 - math.sin(math.rad(d)) * r2,
scrw / 2 + math.cos(math.rad(d)) * r,
scrh / 2 - math.sin(math.rad(d)) * r)
local nadex, nadey = scrw / 2 + math.cos(rad) * ri, scrh / 2 - math.sin(rad) * ri
if !canhighlight(self, slices[i]) or (!nosuicide and i == 2 and bf_suicidelock > 0) then
surface.SetDrawColor(150, 150, 150, a * 200)
end
surface.SetMaterial(slices[i][2])
surface.DrawTexturedRectRotated(nadex, nadey, sg, sg, slices[i][3])
d = d - arcdegrees
end
if !nocenter then
surface.SetDrawColor(255, 255, 255, a * 255)
surface.SetMaterial(mat_none)
surface.DrawTexturedRectRotated(scrw / 2, scrh / 2, TacRP.SS(28), TacRP.SS(28), 0)
end
if !nosuicide and currentind == 2 then
local w, h = TacRP.SS(132), TacRP.SS(24)
local tx, ty = scrw / 2, scrh / 2 + r + TacRP.SS(4)
surface.SetDrawColor(0, 0, 0, 200 * a)
TacRP.DrawCorneredBox(tx - w / 2, ty, w, h, col)
surface.SetTextColor(255, 255, 255, a * 255)
surface.SetFont("TacRP_Myriad_Pro_12")
surface.SetTextColor(255, 255, 255, 255 * a)
local t1 = TacRP:GetPhrase("hint.shootself")
local t1_w = surface.GetTextSize(t1)
surface.SetTextPos(tx - t1_w / 2, ty + TacRP.SS(2))
surface.DrawText(t1)
surface.SetFont("TacRP_Myriad_Pro_6")
if !lastseenfunnyline then
startseefunnylinetime = CurTime()
end
lastseenfunnyline = true
local t2 = bf_funnyline or ""
if bf_suicidelock > 0 then
surface.SetFont("TacRP_Myriad_Pro_8")
t2 = "[ " .. TacRP.GetBind("attack") .. " ] - " .. TacRP:GetPhrase("hint.unlock")
if self:GetCustomize() then
t2 = TacRP:GetPhrase("hint.exitcustmenu")
end
lastseenfunnyline = false
elseif !bf_funnyline then
bf_funnyline = bf_lines[math.random(1, #bf_lines)]
end
local t2_w, t2_h = surface.GetTextSize(t2)
if t2_w > w then
render.SetScissorRect(tx - w / 2, ty, tx + w / 2, ty + h, true)
surface.SetTextPos(tx - ((CurTime() - startseefunnylinetime + 2.5) * w * 0.3) % (t2_w * 2) + (t2_w / 2), ty + TacRP.SS(18) - t2_h / 2)
else
surface.SetTextPos(tx - t2_w / 2, ty + TacRP.SS(18) - t2_h / 2)
end
surface.DrawText(t2)
render.SetScissorRect(0, 0, 0, 0, false)
end
end
hook.Add("VGUIMousePressed", "tacrp_grenademenu", function(pnl, mousecode)
local wpn = LocalPlayer():GetActiveWeapon()
if !(LocalPlayer():Alive() and IsValid(wpn) and wpn.ArcticTacRP and !wpn:StillWaiting(nil, true)) then return end
if wpn.GrenadeMenuAlpha == 1 then
if !TacRP.ConVars["nademenu_click"]:GetBool() or !currentnade then return end
if mousecode == MOUSE_MIDDLE and TacRP.AreTheGrenadeAnimsReadyYet then
local nadewep = currentnade.GrenadeWep
if !nadewep or !wpn:CheckGrenade(currentnade.Index, true) then return end
wpn.GrenadeMenuAlpha = 0
gui.EnableScreenClicker(false)
TacRP.CursorEnabled = false
if LocalPlayer():HasWeapon(nadewep) then
input.SelectWeapon(LocalPlayer():GetWeapon(nadewep))
else
net.Start("tacrp_givenadewep")
net.WriteUInt(currentnade.Index, TacRP.QuickNades_Bits)
net.SendToServer()
wpn.GrenadeWaitSelect = nadewep -- cannot try to switch immediately as the nade wep does not exist on client yet
end
elseif mousecode == MOUSE_RIGHT or mousecode == MOUSE_LEFT then
wpn.GrenadeThrowOverride = mousecode == MOUSE_RIGHT
net.Start("tacrp_togglenade")
net.WriteUInt(currentnade.Index, TacRP.QuickNades_Bits)
net.WriteBool(true)
net.WriteBool(wpn.GrenadeThrowOverride)
net.SendToServer()
wpn.Secondary.Ammo = currentnade.Ammo or "none"
end
elseif wpn.BlindFireMenuAlpha == 1 then
if mousecode == MOUSE_LEFT and currentind == 2 then
bf_suicidelock = bf_suicidelock - 1
end
end
end)

View File

@@ -0,0 +1,162 @@
SWEP.ViewModelVelocityPos = Vector(0, 0, 0)
SWEP.ViewModelVelocityAng = Angle(0, 0, 0)
SWEP.ViewModelPos = Vector(0, 0, 0)
SWEP.ViewModelAng = Angle(0, 0, 0)
SWEP.SwayCT = 0
function SWEP:GetViewModelSway(pos, ang)
local d = Lerp(self:GetSightDelta(), 1, 0.02)
local v = 1
local steprate = 1
local FT = self:DeltaSysTime() * 1 --FrameTime()
local CT = UnPredictedCurTime() -- CurTime()
d = d * 0.25
pos = pos + (ang:Up() * (math.sin(self.SwayCT * 0.311 * v) + math.cos(self.SwayCT * 0.44 * v)) * math.sin(CT * 0.8) * d)
pos = pos + (ang:Right() * (math.sin(self.SwayCT * 0.324 * v) + math.cos(self.SwayCT * 0.214 * v)) * math.sin(CT * 0.76) * d)
--if IsFirstTimePredicted() then
self.SwayCT = self.SwayCT + (FT * steprate)
--end
return pos, ang
end
SWEP.ViewModelLastEyeAng = Angle(0, 0, 0)
SWEP.ViewModelSwayInertia = Angle(0, 0, 0)
function SWEP:GetViewModelInertia(pos, ang)
local d = 1 - self:GetSightDelta()
local diff = self:GetOwner():EyeAngles() - self.ViewModelLastEyeAng
diff = diff / 4
diff.p = math.Clamp(diff.p, -1, 1)
diff.y = math.Clamp(diff.y, -1, 1)
local vsi = self.ViewModelSwayInertia
vsi.p = math.ApproachAngle(vsi.p, diff.p, vsi.p / 10 * FrameTime() / 0.5)
vsi.y = math.ApproachAngle(vsi.y, diff.y, vsi.y / 10 * FrameTime() / 0.5)
self.ViewModelLastEyeAng = self:GetOwner():EyeAngles()
ang:RotateAroundAxis(ang:Up(), vsi.y * 12 * d)
ang:RotateAroundAxis(ang:Right(), -vsi.p * 12 * d)
-- pos = pos - (ang:Up() * vsi.p * 0.5 * d)
-- pos = pos - (ang:Right() * vsi.y * 0.5 * d)
return pos, ang
end
function SWEP:GetViewModelSmooth(pos, ang)
return pos, ang
end
SWEP.ViewModelBobVelocity = 0
SWEP.ViewModelNotOnGround = 0
SWEP.BobCT = 0
function SWEP:GetViewModelBob(pos, ang)
local step = 10
local mag = 1
local FT = self:DeltaSysTime() * 1 --FrameTime()
local CT = UnPredictedCurTime() -- CurTime()
local v = self:GetOwner():GetVelocity():Length()
local walks = self:GetOwner():GetWalkSpeed()
local runs = self:GetOwner():GetRunSpeed()
local sprints = walks + math.max(runs - walks, walks)
v = math.Clamp(v, 0, sprints)
self.ViewModelBobVelocity = math.Approach(self.ViewModelBobVelocity, v, FT * 2400)
local d = math.Clamp(self.ViewModelBobVelocity / sprints, 0, 1)
if self:GetOwner():OnGround() then
self.ViewModelNotOnGround = math.Approach(self.ViewModelNotOnGround, 0, FT / 1)
else
self.ViewModelNotOnGround = math.Approach(self.ViewModelNotOnGround, 1, FT / 1)
end
d = d * Lerp(self:GetSightDelta(), 1, 0.1)
mag = d * 2
step = 10
local m = 0.2
ang:RotateAroundAxis(ang:Forward(), math.sin(self.BobCT * step * 0.5) * ((math.sin(CT * 6.151) * m) + 1) * 4.5 * d)
ang:RotateAroundAxis(ang:Right(), math.sin(self.BobCT * step * 0.12) * ((math.sin(CT * 1.521) * m) + 1) * 2.11 * d)
pos = pos - (ang:Up() * math.sin(self.BobCT * step) * 0.11 * ((math.sin(CT * 3.515) * m) + 1) * mag)
pos = pos + (ang:Forward() * math.sin(self.BobCT * step * 0.5) * 0.11 * ((math.sin(CT * 1.615) * m) + 1) * mag)
pos = pos + (ang:Right() * (math.sin(self.BobCT * step * 0.3) + (math.cos(self.BobCT * step * 0.3332))) * 0.16 * mag)
local steprate = Lerp(d, 1, 2.5)
steprate = Lerp(self.ViewModelNotOnGround, steprate, 0.9)
--if IsFirstTimePredicted() or game.SinglePlayer() then
self.BobCT = self.BobCT + (FT * steprate)
--end
return pos, ang
end
SWEP.LastViewModelVerticalVelocity = 0
-- SWEP.ViewModelLanded = 0
-- SWEP.ViewModelLanding = 0
function SWEP:GetMidAirBob(pos, ang)
local v = -self:GetOwner():GetVelocity().z / 200
v = math.Clamp(v, -1, 1)
-- if v == 0 and self.LastViewModelVerticalVelocity != 0 then
-- self.ViewModelLanding = self.LastViewModelVerticalVelocity
-- self.ViewModelLanded = 1
-- end
-- if self.ViewModelLanded > 0 then
-- self.ViewModelLanded = math.Approach(self.ViewModelLanded, 0, FrameTime() / 0.25)
v = Lerp(5 * FrameTime(), self.LastViewModelVerticalVelocity, v)
-- end
self.LastViewModelVerticalVelocity = v
local d = self.ViewModelNotOnGround
d = d * Lerp(self:GetSightDelta(), 1, 0.1)
ang:RotateAroundAxis(ang:Right(), -v * d * 8 * math.sin(CurTime() * 0.15))
return pos, ang
end
SWEP.ViewModelInertiaX = 0
SWEP.ViewModelInertiaY = 0
function SWEP:GetViewModelLeftRight(pos, ang)
local v = self:GetOwner():GetVelocity()
local d = Lerp(self:GetSightDelta(), 1, 0)
v, _ = WorldToLocal(v, Angle(0, 0, 0), Vector(0, 0, 0), self:GetOwner():EyeAngles())
local vx = math.Clamp(v.x / 200, -1, 1)
local vy = math.Clamp(v.y / 200, -1, 1)
self.ViewModelInertiaX = math.Approach(self.ViewModelInertiaX, vx, math.abs(vx) * FrameTime() / 0.1)
self.ViewModelInertiaY = math.Approach(self.ViewModelInertiaY, vy, math.abs(vy) * FrameTime() / 0.1)
pos = pos + (ang:Right() * -self.ViewModelInertiaX * 0.65 * d)
pos = pos + (ang:Forward() * self.ViewModelInertiaY * 0.5 * d)
return pos, ang
end

View File

@@ -0,0 +1,167 @@
local rt_w = 240
local rt_h = 240
local rtmat = GetRenderTarget("tacrp_pipscope_thermal", rt_w, rt_h, false)
local rtmat_spare = GetRenderTarget("tacrp_pipscope_thermal2", rt_w, rt_h, false)
local lastthermalscope = false
local thermaltime = 0
local csm_boot_1 = Material("tacrp/hud/thermal_boot_1.png", "mips smooth")
local csm_1 = Material("tacrp/hud/thermal_1.png", "mips smooth")
local csm_2 = Material("tacrp/hud/thermal_2.png", "mips smooth")
local noise1 = Material("tacrp/hud/noise1.png")
local noise2 = Material("tacrp/hud/noise2.png")
local noise3 = Material("tacrp/hud/noise3.png")
local noise4 = Material("tacrp/hud/noise4.png")
local noisemats = {
noise1,
noise2,
noise3,
noise4
}
local lastrendertime = 0
local fps = 30
function SWEP:DoThermalRT()
if self:GetScopeLevel() <= 0 or !self:GetPeeking() then lastthermalscope = false return end
if TacRP.OverDraw then return end
if !lastthermalscope then
thermaltime = 0
end
if lastrendertime > CurTime() - (1 / fps) then return end
local angles = self:GetShootDir()
local origin = self:GetMuzzleOrigin()
local rt = {
x = 0,
y = 0,
w = rt_w,
h = rt_h,
aspect = 0.999,
angles = angles,
origin = origin,
drawviewmodel = false,
fov = 18.5,
znear = 6
}
render.PushRenderTarget(rtmat, 0, 0, rt_w, rt_h)
if thermaltime >= 0.75 or thermaltime == 0 then
TacRP.OverDraw = true
render.RenderView(rt)
TacRP.OverDraw = false
end
DrawColorModify({
["$pp_colour_addr"] = 0.25 * 132 / 255,
["$pp_colour_addg"] = 0.25 * 169 / 255,
["$pp_colour_addb"] = 0.25 * 154 / 255,
["$pp_colour_brightness"] = 0.7,
["$pp_colour_contrast"] = 0.75,
["$pp_colour_colour"] = 0,
["$pp_colour_mulr"] = 0,
["$pp_colour_mulg"] = 0,
["$pp_colour_mulb"] = 0
})
DrawBloom(0.25, 0.5, 16, 8, 1, 1, 1, 1, 1)
if thermaltime >= 0.75 then
local thermalents = ents.FindInCone(origin, angles:Forward(), 10000, 0.939692620) // 20 degrees
render.SuppressEngineLighting(true)
render.SetBlend(0.9)
local col = Color(255, 0, 0)
if self:GetTactical() then
col = Color(0, 255, 255)
end
render.SetColorModulation(col.r, col.g, col.b)
cam.Start3D(origin, angles, 20)
cam.IgnoreZ(false)
for _, ent in ipairs(thermalents) do
if ent == self:GetOwner() then continue end
if !ent:IsValid() or ent:IsWorld() then continue end
if ent:Health() <= 0 then continue end
if ent:IsPlayer() or ent:IsNPC() or ent:IsNextBot() or ent:IsOnFire() then
ent:DrawModel()
end
if ent:IsVehicle() or ent:IsOnFire() or ent.ArcCW_Hot or ent:IsScripted() and !ent:GetOwner():IsValid() then
ent:DrawModel()
end
end
cam.End3D()
render.SetColorModulation(1, 1, 1)
render.SuppressEngineLighting(false)
render.MaterialOverride()
render.SetBlend(1)
end
if self:GetTactical() then
render.PushRenderTarget(rtmat, 0, 0, rt_w, rt_h)
render.CopyTexture( rtmat, rtmat_spare )
render.Clear(255, 255, 255, 255, true, true)
render.OverrideBlend(true, BLEND_ONE, BLEND_ONE, BLENDFUNC_REVERSE_SUBTRACT)
render.DrawTextureToScreen(rtmat_spare)
render.OverrideBlend(false)
render.PopRenderTarget()
end
cam.Start2D()
render.ClearDepth()
if thermaltime < 0.75 then
surface.SetDrawColor(0, 0, 0)
surface.DrawRect(0, 0, rt_w, rt_h)
end
if thermaltime < 0.45 then
surface.SetMaterial(csm_boot_1)
else
if self:GetTactical() then
surface.SetMaterial(csm_1)
else
surface.SetMaterial(csm_2)
end
end
surface.SetDrawColor(255, 255, 255)
surface.DrawTexturedRect(0, 0, rt_w, rt_h)
cam.End2D()
render.PopRenderTarget()
thermaltime = thermaltime + (math.random(0, 5) * math.random(0, 5) * (1 / fps) / 6.25)
lastthermalscope = true
lastrendertime = CurTime()
end
function SWEP:DoThermalCam()
if self:GetScopeLevel() <= 0 or !self:GetPeeking() then lastthermalscope = false return end
local w = TacRP.SS(480 / 4)
local h = TacRP.SS(480 / 4)
local x = (ScrW() - w) / 2
local y = (ScrH() - h) / 2
render.DrawTextureToScreenRect(rtmat, x, y, w, h)
end

View File

@@ -0,0 +1,241 @@
function SWEP:ViewModelDrawn()
if IsValid(self.QuickNadeModel) then
self.QuickNadeModel:DrawModel()
end
self:DrawCustomModel(false)
self:DrawLasers()
local newactiveeffects = {}
for _, effect in ipairs(self.ActiveEffects) do
if !IsValid(effect) then continue end
if !effect.VMContext then continue end
effect:DrawModel()
table.insert(newactiveeffects, effect)
end
self.ActiveEffects = newactiveeffects
end
function SWEP:DrawCustomModel(wm, custom_wm)
if !wm and !IsValid(self:GetOwner()) then return end
if !wm and self:GetOwner():IsNPC() then return end
local mdl = self.VModel
if wm then
mdl = self.WModel
end
if !mdl then
self:SetupModel(wm, custom_wm)
mdl = self.VModel
if wm then
mdl = self.WModel
end
end
local parentmdl = self
if !wm then
parentmdl = self:GetVM()
elseif custom_wm then
parentmdl = custom_wm
end
if !mdl then return end
for _, model in pairs(mdl) do
if !IsValid(model) then continue end
local offset_pos = model.Pos
local offset_ang = model.Ang
local bone = model.Bone
local atttbl = {}
local slottbl = {}
if model.WMBase then
parentmdl = self:GetOwner()
end
parentmdl:SetupBones()
parentmdl:InvalidateBoneCache()
if !offset_pos or !offset_ang then
local slot = model.Slot
slottbl = self.Attachments[slot]
atttbl = TacRP.GetAttTable(self.Attachments[slot].Installed)
bone = slottbl.Bone
if wm then
bone = slottbl.WMBone or "ValveBiped.Bip01_R_Hand"
end
offset_pos = slottbl.Pos_VM
offset_ang = slottbl.Ang_VM
if wm then
offset_pos = slottbl.Pos_WM
offset_ang = slottbl.Ang_WM
end
for _, ele in ipairs(self:GetElements()) do
if !ele.AttPosMods or !ele.AttPosMods[slot] then continue end
if wm then
if ele.AttPosMods[slot].Pos_WM then
offset_pos = ele.AttPosMods[slot].Pos_WM
end
if ele.AttPosMods[slot].Ang_WM then
offset_ang = ele.AttPosMods[slot].Ang_WM
end
if ele.AttPosMods[slot].WMBone then
bone = ele.AttPosMods[slot].WMBone
end
else
if ele.AttPosMods[slot].Pos_VM then
offset_pos = ele.AttPosMods[slot].Pos_VM
end
if ele.AttPosMods[slot].Ang_VM then
offset_ang = ele.AttPosMods[slot].Ang_VM
end
if ele.AttPosMods[slot].Bone then
bone = ele.AttPosMods[slot].Bone
end
end
end
end
if !bone then continue end
local boneindex = parentmdl:LookupBone(bone)
if !boneindex then continue end
local bonemat = parentmdl:GetBoneMatrix(boneindex)
if !bonemat then continue end
local bpos, bang
bpos = bonemat:GetTranslation()
bang = bonemat:GetAngles()
local apos, aang = bpos, bang
if offset_pos then
apos:Add(bang:Forward() * offset_pos.x)
apos:Add(bang:Right() * offset_pos.y)
apos:Add(bang:Up() * offset_pos.z)
end
if offset_ang then
aang:RotateAroundAxis(aang:Right(), offset_ang.p)
aang:RotateAroundAxis(aang:Up(), offset_ang.y)
aang:RotateAroundAxis(aang:Forward(), offset_ang.r)
end
local moffset = (atttbl.ModelOffset or Vector(0, 0, 0))
if wm then
moffset = moffset * (slottbl.WMScale or 1)
else
moffset = moffset * (slottbl.VMScale or 1)
end
apos:Add(aang:Forward() * moffset.x)
apos:Add(aang:Right() * moffset.y)
apos:Add(aang:Up() * moffset.z)
model:SetPos(apos)
model:SetAngles(aang)
model:SetRenderOrigin(apos)
model:SetRenderAngles(aang)
if model.IsHolosight and !wm then
cam.Start3D(EyePos(), EyeAngles(), self.ViewModelFOV, 0, 0, nil, nil, 1, 10000)
render.DepthRange(0.0, 0.1)
self:DoHolosight(model)
cam.End3D()
render.DepthRange(0.0, 0.1)
end
if !model.NoDraw then
model:DrawModel()
end
end
if !wm then
self:DrawFlashlightsVM()
end
end
function SWEP:PreDrawViewModel()
if self:GetValue("ScopeHideWeapon") and self:IsInScope() then
render.SetBlend(0)
end
-- Apparently setting this will fix the viewmodel position and angle going all over the place in benchgun.
if TacRP.ConVars["dev_benchgun"]:GetBool() then
if self.OriginalViewModelFOV == nil then
self.OriginalViewModelFOV = self.ViewModelFOV
end
self.ViewModelFOV = self:GetOwner():GetFOV()
elseif self.OriginalViewModelFOV then
self.ViewModelFOV = self.OriginalViewModelFOV
self.OriginalViewModelFOV = nil
end
-- self.ViewModelFOV = self:GetViewModelFOV()
render.DepthRange(0.0, 0.1)
end
function SWEP:PostDrawViewModel()
cam.IgnoreZ(false)
if self:GetValue("ScopeHideWeapon") and self:IsInScope() then
render.SetBlend(1)
end
cam.Start3D()
cam.IgnoreZ(false)
local newpcfs = {}
for _, pcf in ipairs(self.PCFs) do
if IsValid(pcf) then
pcf:Render()
table.insert(newpcfs, pcf)
end
end
if !inrt then self.PCFs = newpcfs end
local newmzpcfs = {}
for _, pcf in ipairs(self.MuzzPCFs) do
if IsValid(pcf) then
pcf:Render()
table.insert(newmzpcfs, pcf)
end
end
if !inrt then self.MuzzPCFs = newmzpcfs end
cam.End3D()
end
--[[
SWEP.SmoothedViewModelFOV = nil
function SWEP:GetViewModelFOV()
local target = self.ViewModelFOV
if TacRP.ConVars["dev_benchgun"]:GetBool() then
target = self:GetOwner():GetFOV()
end
self.SmoothedViewModelFOV = self.SmoothedViewModelFOV or target
local diff = math.abs(target - self.SmoothedViewModelFOV)
self.SmoothedViewModelFOV = math.Approach(self.SmoothedViewModelFOV, target, diff * FrameTime() / 0.25)
return self.SmoothedViewModelFOV
end
]]

View File

@@ -0,0 +1,35 @@
function SWEP:DrawWorldModel(flags)
if !self.CertainAboutAtts and !self.AskedAboutAtts then
if !self:GetValue("PrimaryGrenade") and !self:GetValue("PrimaryMelee") then
self:RequestWeapon()
-- debugoverlay.Sphere(self:GetPos(), 16, 5, color_white, true)
end
self.AskedAboutAtts = true
end
-- Ugly workaround: OBS_MODE_IN_EYE spectate seems to call DrawWorldModel but doesn't actually render it?
if LocalPlayer():GetObserverTarget() != self:GetOwner() or LocalPlayer():GetObserverMode() != OBS_MODE_IN_EYE then
self:DrawCustomModel(true)
end
if self:GetValue("Laser") and self:GetTactical() then
self:SetRenderBounds(Vector(-16, -16, -16), Vector(16, 16, 15000))
else
self:SetRenderBounds(Vector(-16, -16, -16), Vector(16, 16, 16))
end
self:DrawModel()
end
hook.Add("PostDrawTranslucentRenderables", "TacRP_TranslucentDraw", function()
for _, ply in pairs(player.GetAll()) do
local wep = ply:GetActiveWeapon()
if ply != LocalPlayer() and IsValid(wep) and wep.ArcticTacRP then
wep:DrawLasers(true)
wep:DrawFlashlightsWM()
wep:DrawFlashlightGlares()
wep:DoScopeGlint()
end
end
end)

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,88 @@
function SWEP:PlayAnimation(seq, mult, lock, doidle)
mult = mult or 1
lock = lock or false
local anim = self:TranslateSequence(seq)
doidle = doidle or false
local reverse = false
if mult < 0 then
reverse = true
mult = -mult
end
local vm = self:GetVM()
if !IsValid(vm) then return end
if isstring(anim) then
seq = vm:LookupSequence(anim)
end
if seq == -1 then return end
self.CurrentAnimation = anim
self.CurrentSeqeunce = seq
local time = vm:SequenceDuration(seq)
time = time * mult
vm:SendViewModelMatchingSequence(seq)
if reverse then
vm:SetCycle(1)
vm:SetPlaybackRate(-1 / mult)
else
vm:SetCycle(0)
vm:SetPlaybackRate(1 / mult)
end
if lock then
self:SetAnimLockTime(CurTime() + time)
-- self:SetNextSecondaryFire(CurTime() + time)
else
self:SetAnimLockTime(0)
-- self:SetNextSecondaryFire(0)
end
if doidle and !self.NoIdle then
self:SetNextIdle(CurTime() + time)
else
self:SetNextIdle(math.huge)
end
self:SetLastProceduralFireTime(0)
return time
end
function SWEP:IdleAtEndOfAnimation()
local vm = self:GetVM()
local cyc = vm:GetCycle()
local duration = vm:SequenceDuration()
local rate = vm:GetPlaybackRate()
local time = (1 - cyc) * (duration / rate)
self:SetNextIdle(CurTime() + time)
end
function SWEP:Idle()
if self:GetPrimedGrenade() then return end
if self:GetBlindFire() then
if self:Clip1() == 0 then
self:PlayAnimation("blind_dryfire", 0, false, false)
else
self:PlayAnimation("blind_idle")
end
else
if self:Clip1() == 0 then
self:PlayAnimation("dryfire", 0, false, false)
else
self:PlayAnimation("idle")
end
end
self:SetReady(true)
end

View File

@@ -0,0 +1,20 @@
function SWEP:TranslateSequence(seq)
seq = self:RunHook("Hook_TranslateSequence", seq)
seq = self.AnimationTranslationTable[seq] or seq
if istable(seq) then
seq["BaseClass"] = nil
seq = seq[math.Round(util.SharedRandom("TacRP_animtr", 1, #seq))]
end
return seq
end
function SWEP:HasSequence(seq)
seq = self:TranslateSequence(seq)
local vm = self:GetVM()
seq = vm:LookupSequence(seq)
return seq != -1
end

View File

@@ -0,0 +1,201 @@
function SWEP:Attach(slot, att, silent, suppress)
local slottbl = self.Attachments[slot]
if slottbl.Installed then return end
if !self:CanAttach(slot, att) then return end
local atttbl = TacRP.GetAttTable(att)
if !atttbl then return end
if TacRP:PlayerGetAtts(self:GetOwner(), att) <= 0 then return end
local inf_old = self:GetInfiniteAmmo()
local ammo_old = self:GetAmmoType()
slottbl.Installed = att
TacRP:PlayerTakeAtt(self:GetOwner(), att, 1)
if atttbl.OnAttach then
atttbl.OnAttach(self)
end
if CLIENT then
local attid = atttbl.ID
net.Start("TacRP_attach")
net.WriteEntity(self)
net.WriteBool(true)
net.WriteUInt(slot, 8)
net.WriteUInt(attid, TacRP.Attachments_Bits)
net.SendToServer()
if game.SinglePlayer() then -- Due to bodygroups also being networked by engine, this will cause bodygroup "flickering"
self:SetupModel(true)
self:SetupModel(false)
end
if !silent then
surface.PlaySound(slottbl.AttachSound or "")
end
elseif SERVER and !suppress then
self:NetworkWeapon()
TacRP:PlayerSendAttInv(self:GetOwner())
end
self:SetBurstCount(0)
self:InvalidateCache()
self:SetBaseSettings()
if atttbl.CanToggle then
self:SetTactical(true)
end
if self:GetFiremode() > self:GetFiremodeAmount() then
self:SetFiremode(1)
end
local inf_new = self:GetInfiniteAmmo()
local ammo_new = self:GetAmmoType()
if SERVER then
if inf_old and !inf_new then
self:SetClip1(0)
elseif (inf_new and !inf_old) or (ammo_old != ammo_new) then
self:Unload(ammo_old)
end
end
end
function SWEP:Detach(slot, silent, suppress)
local slottbl = self.Attachments[slot]
if !slottbl.Installed then return end
if !self:CanDetach(slot, slottbl.Installed) then return end
TacRP:PlayerGiveAtt(self:GetOwner(), slottbl.Installed, 1)
local inf_old = self:GetInfiniteAmmo()
local ammo_old = self:GetAmmoType()
local atttbl = TacRP.GetAttTable(slottbl.Installed)
if atttbl and atttbl.OnDetach then
atttbl.OnDetach(self)
end
slottbl.Installed = nil
if CLIENT then
net.Start("TacRP_attach")
net.WriteEntity(self)
net.WriteBool(false)
net.WriteUInt(slot, 8)
net.SendToServer()
if game.SinglePlayer() then -- Due to bodygroups also being networked by engine, this will cause bodygroup "flickering"
self:SetupModel(true)
self:SetupModel(false)
end
if !silent then
surface.PlaySound(slottbl.DetachSound or "")
end
elseif SERVER and !suppress then
self:NetworkWeapon()
TacRP:PlayerSendAttInv(self:GetOwner())
end
self:SetBurstCount(0)
self:InvalidateCache()
self:SetBaseSettings()
if self:GetFiremode() > self:GetFiremodeAmount() then
self:SetFiremode(1)
end
local nade = self:GetGrenade()
if (nade.AdminOnly and self:GetOwner():GetAmmoCount(nade.Ammo) <= 0) or (nade.RequireStat and !self:GetValue(nade.RequireStat)) then
self:SelectGrenade()
end
local inf_new = self:GetInfiniteAmmo()
local ammo_new = self:GetAmmoType()
if SERVER then
if inf_old and !inf_new then
self:SetClip1(0)
elseif (inf_new and !inf_old) or (ammo_old != ammo_new) then
self:Unload(ammo_old)
end
end
end
function SWEP:ToggleCustomize(on)
if on == self:GetCustomize() or (on and self:GetValue("RunawayBurst") and self:GetBurstCount() > 0) then return end
self:ScopeToggle(0)
self:ToggleBlindFire(TacRP.BLINDFIRE_NONE)
self:SetCustomize(on)
self:SetShouldHoldType()
end
function SWEP:CanAttach(slot, att)
local atttbl = TacRP.GetAttTable(att)
local slottbl = self.Attachments[slot]
if atttbl.Compatibility then
local result = atttbl.Compatibility(self)
if result == true then
return true
elseif result == false then
return false
end
end
local cat = slottbl.Category
if !istable(cat) then
cat = {cat}
end
local attcat = atttbl.Category
if !istable(attcat) then
attcat = {attcat}
end
if !TacRP.CanCustomize(self:GetOwner(), self, att, slot) then return false end
for _, c in pairs(attcat) do
if table.HasValue(cat, c) then
return true
end
end
return false
end
function SWEP:CanDetach(slot, att)
local slottbl = self.Attachments[slot]
if slottbl.Integral then return false end
if !TacRP.CanCustomize(self:GetOwner(), self, att, slot, true) then return false end
return true
end
function SWEP:ToggleTactical()
local ret = self:RunHook("Hook_ToggleTactical")
if !ret then
self:EmitSound(self:GetValue("Sound_ToggleTactical"))
self:SetTactical(!self:GetTactical())
end
end

View File

@@ -0,0 +1,95 @@
SWEP.LockOnEntity = NULL
SWEP.LastSearchTime = 0
SWEP.PlayedLockOnSound = false
function SWEP:ThinkLockOn()
local owner = self:GetOwner()
local lastlockonentity = self:GetLockOnEntity()
if CLIENT then
if !IsValid(self:GetLockOnEntity()) then
self.PlayedLockOnSound = false
end
end
if not ((self:GetSightAmount() >= 1 and self:GetValue("LockOnInSights")) or (self:GetSightAmount() < 1 and self:GetValue("LockOnOutOfSights"))) then
self:SetLockOnEntity(nil)
self:SetLockOnStartTime(CurTime())
else
local lockontarget = nil
if lastlockonentity and IsValid(lastlockonentity) then
// check if it remains within seeker cage
local player_aim_vector = owner:GetAimVector()
local target_angle = math.deg(math.acos(player_aim_vector:Dot((lastlockonentity:WorldSpaceCenter() - owner:GetShootPos()):GetNormalized())))
local dist = (lastlockonentity:WorldSpaceCenter() - owner:GetShootPos()):Length()
if target_angle < self:GetValue("LockOnTrackAngle") and dist < self:GetValue("LockOnRange") then
lockontarget = lastlockonentity
end
else
local tr = util.TraceLine(
{
start = owner:GetShootPos(),
endpos = owner:GetShootPos() + owner:GetAimVector() * self:GetValue("LockOnRange"),
ignoreworld = true,
filter = function(target)
if target == owner then return false end
if target:IsPlayer() then return true end
if (target:IsNPC() or target:IsNextBot()) then return true end
if (target.LVS and target:GetHP() > 0) or target.Targetable then return true end
if target.IsGlideVehicle then return true end
if TacRP.LockableEntities[target:GetClass()] then return true end
if TacRP.FlareEntities[target:GetClass()] or target.IsTacRPFlare then return true end
end
}
)
lockontarget = tr.Entity
end
if lockontarget and IsValid(lockontarget) then
local occlusion_tr = util.TraceLine({
start = owner:GetShootPos(),
endpos = lockontarget:WorldSpaceCenter(),
mask = MASK_SHOT,
filter = function(ent)
if ent == lockontarget or ent == owner or ent:GetOwner() == lockontarget then return false end
if ent:IsVehicle() and ent:GetDriver() == owner then return false end
if ent:GetClass() == "lvs_wheeldrive_wheel" or scripted_ents.IsBasedOn(ent:GetClass(), "tacrp_proj_base") then return false end
return true
end
})
if occlusion_tr.Hit then lockontarget = nil end
end
if lockontarget and IsValid(lockontarget) then
if lastlockonentity != lockontarget then
self:SetLockOnStartTime(CurTime())
if CLIENT and (IsFirstTimePredicted() or game.SinglePlayer()) then
self:EmitSound(self:GetValue("Sound_StartLockOn"))
end
elseif not self.PlayedLockOnSound and CurTime() > self:GetLockOnStartTime() + self:GetValue("LockOnTime") then
if CLIENT and (IsFirstTimePredicted() or game.SinglePlayer()) then
self:EmitSound(self:GetValue("Sound_FinishLockOn"))
self.PlayedLockOnSound = true
end
end
self:SetLockOnEntity(lockontarget)
self.LockOnEntity = lockontarget
else
self:SetLockOnEntity(nil)
self.PlayedLockOnSound = false
self:SetLockOnStartTime(CurTime())
end
end
if not IsValid(self:GetLockOnEntity()) then
self:SetLockOnEntity(nil)
self:SetLockOnStartTime(CurTime())
end
end

View File

@@ -0,0 +1,132 @@
function SWEP:InBipod()
local bip = self:GetInBipod()
-- if !self:CanBipod() then
-- self:ExitBipod()
-- end
if IsValid(self:GetOwner()) and (self:GetOwner():GetVelocity():LengthSqr() >= 100 or self:GetSprintAmount() > 0) then
self:ExitBipod()
end
return bip
end
SWEP.CachedCanBipod = true
SWEP.CachedCanBipodTime = 0
SWEP.LastBipodTime = 0
local dist = 24
function SWEP:CanBipod()
if !self:GetValue("Bipod") then return false end
if self:GetOwner():InVehicle() then return false end
if self:GetSprintAmount() > 0 and !self:DoForceSightsBehavior() then return false end
if self.CachedCanBipodTime >= CurTime() then return tobool(self.CachedCanBipod), self.CachedCanBipod end
local pos = self:GetOwner():EyePos()
local angle = self:GetOwner():EyeAngles()
if math.abs(angle.p) <= 45 then
angle.p = 0
end
if self:GetOwner():GetVelocity():Length() > 0 then
return false
end
local rangemult = 2
if self:IsProne() then
rangemult = rangemult * 1.25
end
local tr = util.TraceLine({
start = pos,
endpos = pos + (angle:Forward() * dist * rangemult),
filter = self:GetOwner(),
mask = MASK_PLAYERSOLID
})
if tr.Hit then -- check for stuff in front of us
return false
end
local maxs = Vector(10, 10, 16)
local mins = Vector(-10, -10, 0)
angle.p = angle.p + 45
tr = util.TraceHull({
start = pos,
endpos = pos + (angle:Forward() * dist * rangemult),
filter = self:GetOwner(),
maxs = maxs,
mins = mins,
mask = MASK_PLAYERSOLID
})
self.CachedCanBipodTime = CurTime()
if tr.Hit then
local tr2 = util.TraceHull({
start = tr.HitPos,
endpos = tr.HitPos + Vector(0, 0, -dist),
filter = self:GetOwner(),
maxs = maxs,
mins = mins,
mask = MASK_PLAYERSOLID
})
if tr2.Hit then
self.CachedCanBipod = tr2
return true, tr2
end
end
self.CachedCanBipod = false
return false
end
function SWEP:EnterBipod(sp)
if !sp and self:GetInBipod() then return end
local can, tr = self:CanBipod()
if !sp and !can then return end
if SERVER and game.SinglePlayer() then self:CallOnClient("EnterBipod", "true") end
self.LastBipodTime = CurTime()
local owner = self:GetOwner()
local bipodang = tr.HitNormal:Cross(owner:EyeAngles():Right()):Angle()
-- bipodang.p = math.ApproachAngle(bipodang.p, owner:EyeAngles().p, 10)
debugoverlay.Axis(tr.HitPos, tr.HitNormal:Angle(), 16, 5, true)
debugoverlay.Line(tr.HitPos, tr.HitPos + bipodang:Forward() * 32, 5, color_white, true)
debugoverlay.Line(tr.HitPos, tr.HitPos + owner:EyeAngles():Forward() * 32, 5, Color(255, 255, 0), true)
self:SetBipodPos(owner:EyePos() + (owner:EyeAngles():Forward() * 4) - Vector(0, 0, 3))
self:SetBipodAngle(bipodang)
if game.SinglePlayer() and CLIENT then return end
self:EmitSound(self.Sound_BipodDown, 70, 100, 1, CHAN_ITEM)
self:SetInBipod(true)
self:DoBodygroups()
end
function SWEP:ExitBipod(sp)
if !sp and !self:GetInBipod() then return end
if SERVER and game.SinglePlayer() then self:CallOnClient("ExitBipod", "true") end
self.LastBipodTime = CurTime()
if game.SinglePlayer() and CLIENT then return end
self:EmitSound(self.Sound_BipodUp, 70, 100, 1, CHAN_ITEM)
self:SetInBipod(false)
self:DoBodygroups()
end
function SWEP:IsProne()
if PRONE_INPRONE then
return self:GetOwner().IsProne and self:GetOwner():IsProne()
else
return false
end
end

View File

@@ -0,0 +1,285 @@
function SWEP:GetMuzzleOrigin()
if !IsValid(self:GetOwner()) then
return self:GetPos()
end
if self:GetOwner():IsNPC() then
return SERVER and self:GetOwner():GetShootPos() or self:GetOwner():EyePos()
end
local pos = self:GetOwner():EyePos()
if self:GetBlindFire() then
local eyeang = self:GetOwner():EyeAngles()
local testpos = pos + eyeang:Up() * 24
if self:GetBlindFireLeft() or self:GetBlindFireRight() then
testpos = pos + eyeang:Forward() * 24
end
local tr = util.TraceLine({
start = pos,
endpos = testpos,
filter = self:GetOwner()
})
pos = tr.HitPos
end
local offset = self:GetValue("ShootOffset")
if offset.x != 0 then
pos = pos + self:GetOwner():GetRight() * offset.x
end
if offset.y != 0 then
pos = pos + self:GetOwner():GetForward() * offset.y
end
if offset.z != 0 then
pos = pos + self:GetOwner():GetUp() * offset.z
end
return pos
end
/*
ValveBiped.Bip01_Spine
ValveBiped.Bip01_Spine1
ValveBiped.Bip01_Spine2
ValveBiped.Bip01_Spine4
ValveBiped.Bip01_Neck1
ValveBiped.Bip01_Head1
ValveBiped.forward
ValveBiped.Bip01_R_Clavicle
ValveBiped.Bip01_R_UpperArm
ValveBiped.Bip01_R_Forearm
ValveBiped.Bip01_R_Hand
ValveBiped.Anim_Attachment_RH
ValveBiped.Bip01_L_Clavicle
ValveBiped.Bip01_L_UpperArm
ValveBiped.Bip01_L_Forearm
ValveBiped.Bip01_L_Hand
ValveBiped.Anim_Attachment_LH
ValveBiped.Bip01_R_Thigh
ValveBiped.Bip01_R_Calf
ValveBiped.Bip01_R_Foot
ValveBiped.Bip01_R_Toe0
ValveBiped.Bip01_L_Thigh
ValveBiped.Bip01_L_Calf
ValveBiped.Bip01_L_Foot
ValveBiped.Bip01_L_Toe0
ValveBiped.Bip01_L_Finger4
ValveBiped.Bip01_L_Finger41
ValveBiped.Bip01_L_Finger42
ValveBiped.Bip01_L_Finger3
ValveBiped.Bip01_L_Finger31
ValveBiped.Bip01_L_Finger32
ValveBiped.Bip01_L_Finger2
ValveBiped.Bip01_L_Finger21
ValveBiped.Bip01_L_Finger22
ValveBiped.Bip01_L_Finger1
ValveBiped.Bip01_L_Finger11
ValveBiped.Bip01_L_Finger12
ValveBiped.Bip01_L_Finger0
ValveBiped.Bip01_L_Finger01
ValveBiped.Bip01_L_Finger02
ValveBiped.Bip01_R_Finger4
ValveBiped.Bip01_R_Finger41
ValveBiped.Bip01_R_Finger42
ValveBiped.Bip01_R_Finger3
ValveBiped.Bip01_R_Finger31
ValveBiped.Bip01_R_Finger32
ValveBiped.Bip01_R_Finger2
ValveBiped.Bip01_R_Finger21
ValveBiped.Bip01_R_Finger22
ValveBiped.Bip01_R_Finger1
ValveBiped.Bip01_R_Finger11
ValveBiped.Bip01_R_Finger12
ValveBiped.Bip01_R_Finger0
ValveBiped.Bip01_R_Finger01
ValveBiped.Bip01_R_Finger02
*/
local bone_list = {
"ValveBiped.Bip01_R_UpperArm",
"ValveBiped.Bip01_R_Forearm",
"ValveBiped.Bip01_R_Hand",
"ValveBiped.Bip01_L_UpperArm",
"ValveBiped.Bip01_L_Forearm",
"ValveBiped.Bip01_L_Hand",
}
local bone_mods = {
-- ["ValveBiped.Bip01_R_UpperArm"] = Angle(0, -70, 0),
-- ["ValveBiped.Bip01_R_Hand"] = Angle(-55, 45, -90),
["ValveBiped.Bip01_R_UpperArm"] = Angle(45, -90, 0),
["ValveBiped.Bip01_R_Hand"] = Angle(-90, 0, 0),
}
local bone_mods_left = {
-- ["ValveBiped.Bip01_R_UpperArm"] = Angle(0, -70, 0),
-- ["ValveBiped.Bip01_R_Hand"] = Angle(-55, 45, -90),
["ValveBiped.Bip01_R_UpperArm"] = Angle(45, 0, 0),
["ValveBiped.Bip01_R_Forearm"] = Angle(0, 0, 0),
["ValveBiped.Bip01_R_Hand"] = Angle(0, -75, 0),
}
local bone_mods_right = {
["ValveBiped.Bip01_R_UpperArm"] = Angle(-45, 0, 0),
["ValveBiped.Bip01_R_Forearm"] = Angle(0, 0, 0),
["ValveBiped.Bip01_R_Hand"] = Angle(35, 75, 0),
}
local bone_mods_kys = {
["ValveBiped.Bip01_R_UpperArm"] = Angle(5, 0, 0),
["ValveBiped.Bip01_R_Forearm"] = Angle(0, -5, 0),
["ValveBiped.Bip01_R_Hand"] = Angle(0, -165, 0),
}
local bone_mods_kys_pistol = {
["ValveBiped.Bip01_R_UpperArm"] = Angle(55, 0, 0),
["ValveBiped.Bip01_R_Forearm"] = Angle(0, -75, 5),
["ValveBiped.Bip01_R_Hand"] = Angle(45, -75, 0),
}
local bone_mods_kys_dual = {
["ValveBiped.Bip01_L_UpperArm"] = Angle(-60, 0, -45),
["ValveBiped.Bip01_L_Forearm"] = Angle(0, -60, -30),
["ValveBiped.Bip01_L_Hand"] = Angle(-30, -45, -90),
["ValveBiped.Bip01_R_UpperArm"] = Angle(55, 0, 30),
["ValveBiped.Bip01_R_Forearm"] = Angle(0, -60, 30),
["ValveBiped.Bip01_R_Hand"] = Angle(45, -75, 90),
}
local bone_mods_index = {
[TacRP.BLINDFIRE_UP] = bone_mods,
[TacRP.BLINDFIRE_LEFT] = bone_mods_left,
[TacRP.BLINDFIRE_RIGHT] = bone_mods_right,
[TacRP.BLINDFIRE_KYS] = bone_mods_kys,
}
function SWEP:ToggleBoneMods(on)
if !IsValid(self:GetOwner()) then return end
if on == TacRP.BLINDFIRE_NONE or on == false or on == nil then
for _, i in ipairs(bone_list) do
local boneindex = self:GetOwner():LookupBone(i)
if !boneindex then continue end
self:GetOwner():ManipulateBoneAngles(boneindex, Angle(0, 0, 0))
-- self:GetOwner():ManipulateBonePosition(boneindex, Vector(0, 0, 0))
end
else
local tbl = bone_mods_index[on]
if on == TacRP.BLINDFIRE_KYS and self:GetValue("HoldTypeSuicide") == "duel" then
tbl = bone_mods_kys_dual
elseif on == TacRP.BLINDFIRE_KYS and self:GetValue("HoldType") == "revolver" then
tbl = bone_mods_kys_pistol
end
for i, k in pairs(tbl) do
local boneindex = self:GetOwner():LookupBone(i)
if !boneindex then continue end
self:GetOwner():ManipulateBoneAngles(boneindex, k)
end
-- for i, k in pairs(tbl[2]) do
-- local boneindex = self:GetOwner():LookupBone(i)
-- if !boneindex then continue end
-- self:GetOwner():ManipulateBonePosition(boneindex, k)
-- end
end
end
function SWEP:GetBlindFireMode()
if !self:GetBlindFire() then
return TacRP.BLINDFIRE_NONE
elseif self:GetBlindFireLeft() and self:GetBlindFireRight() then
return TacRP.BLINDFIRE_KYS
elseif self:GetBlindFireLeft() then
return TacRP.BLINDFIRE_LEFT
elseif self:GetBlindFireRight() then
return TacRP.BLINDFIRE_RIGHT
else
return TacRP.BLINDFIRE_UP
end
end
local bfmode = {
[TacRP.BLINDFIRE_NONE] = {false, false, false},
[TacRP.BLINDFIRE_UP] = {true, false, false},
[TacRP.BLINDFIRE_LEFT] = {true, true, false},
[TacRP.BLINDFIRE_RIGHT] = {true, false, true},
[TacRP.BLINDFIRE_KYS] = {true, true, true},
}
function SWEP:SetBlindFireMode(mode)
if !bfmode[mode] then
print("[TacRP] WARNING! Trying to set invalid blindfire mode: " .. tostring(mode))
mode = 0
end
self:SetBlindFire(bfmode[mode][1])
self:SetBlindFireLeft(bfmode[mode][2])
self:SetBlindFireRight(bfmode[mode][3])
end
function SWEP:CheckBlindFire(suicide)
if !self:GetValue("CanBlindFire") and (!suicide or !self:GetValue("CanSuicide")) then return false end
if (self:GetIsSprinting()
or self:GetAnimLockTime() > CurTime()
or self:GetPrimedGrenade()
or self:IsInScope()
or self:GetSafe()) then
return false
end
return true
end
function SWEP:ToggleBlindFire(bf)
local kms = bf == TacRP.BLINDFIRE_KYS or bf == TacRP.BLINDFIRE_NONE
if bf != TacRP.BLINDFIRE_NONE and (!self:CheckBlindFire(kms) or bf == self:GetBlindFireMode()) then return end
local diff = bf != self:GetBlindFireMode()
if diff then
self:ToggleCustomize(false)
self:ScopeToggle(0)
self:SetBlindFireFinishTime(CurTime() + (bf == TacRP.BLINDFIRE_KYS and 1 or 0.3))
end
self:SetBlindFireMode(bf)
self:ToggleBoneMods(bf)
self:SetShouldHoldType()
if bf == TacRP.BLINDFIRE_KYS and TacRP.ShouldWeFunny() then
self:GetOwner():EmitSound("tacrp/low-tier-god.mp3", 80, 100)
end
if diff then
if self:StillWaiting(true) then
self:IdleAtEndOfAnimation()
else
self:Idle()
end
end
end
function SWEP:ThinkBlindFire()
if (self:GetOwner():KeyDown(IN_ZOOM) or self:GetOwner().TacRPBlindFireDown) and !tobool(self:GetOwner():GetInfo("tacrp_blindfiremenu")) then
if CLIENT then self.LastHintLife = CurTime() end
if self:GetOwner():KeyDown(IN_FORWARD) then
self:ToggleBlindFire(TacRP.BLINDFIRE_UP)
elseif self:GetOwner():KeyDown(IN_MOVELEFT) and !self:GetOwner():KeyDown(IN_MOVERIGHT) then
self:ToggleBlindFire(TacRP.BLINDFIRE_LEFT)
elseif self:GetOwner():KeyDown(IN_MOVERIGHT) and !self:GetOwner():KeyDown(IN_MOVELEFT) then
self:ToggleBlindFire(TacRP.BLINDFIRE_RIGHT)
elseif self:GetOwner():KeyDown(IN_SPEED) and self:GetOwner():KeyDown(IN_WALK) and !tobool(self:GetOwner():GetInfo("tacrp_idunwannadie")) then
self:ToggleBlindFire(TacRP.BLINDFIRE_KYS)
elseif self:GetOwner():KeyDown(IN_BACK) then
self:ToggleBlindFire(TacRP.BLINDFIRE_NONE)
end
elseif (self:GetOwner():KeyDown(IN_ZOOM) or self:GetOwner().TacRPBlindFireDown) and self:GetOwner():GetInfo("tacrp_blindfiremenu") and self:GetOwner():GetCanZoom() then
self:GetOwner():SetCanZoom(false)
end
end

View File

@@ -0,0 +1,113 @@
function SWEP:DoBodygroups(wm, custom_wm)
if wm == nil then
wm = false
self:DoBodygroups(true)
end
if !wm and (!IsValid(self:GetOwner()) or self:GetOwner():IsNPC()) then return end
local dbg = self:GetValue("DefaultBodygroups")
local mdl
if wm then
mdl = custom_wm or self
dbg = self:GetValue("DefaultWMBodygroups")
else
mdl = self:GetVM()
end
if !IsValid(mdl) then return end
mdl:SetBodyGroups(dbg or "")
local sk = self:GetValue("DefaultSkin")
local eles = self:GetElements()
for i, k in ipairs(eles) do
if wm then
for _, j in pairs(k.BGs_WM or {}) do
if _ == "BaseClass" then continue end
mdl:SetBodygroup(j[1], j[2] or 0)
end
if k.Skin_WM != nil then sk = k.Skin_WM end
else
for _, j in pairs(k.BGs_VM or {}) do
if _ == "BaseClass" then continue end
mdl:SetBodygroup(j[1] or 0, j[2] or 0)
end
if k.Skin_VM != nil then sk = k.Skin_VM end
end
end
mdl:SetSkin(sk)
local bbg = self:GetValue("BulletBodygroups")
if bbg then
local amt = self:Clip1()
if self:GetReloading() then
amt = self:GetLoadedRounds()
end
for c, bgs in pairs(bbg) do
if amt < c then
mdl:SetBodygroup(bgs[1], bgs[2])
if !self.BulletBodygroupsSetAll then
break
end
end
end
end
self:RunHook("Hook_PostDoBodygroups")
end
function SWEP:GetElements(holster)
if !self.AttachmentElements then return {} end
local eles = {}
for i, k in pairs(self.Attachments) do
if k.Installed then
table.Add(eles, k.InstalledElements or {})
local atttbl = TacRP.GetAttTable(k.Installed)
table.Add(eles, atttbl.InstalledElements or {})
else
table.Add(eles, k.UnInstalledElements or {})
end
end
local eleatts = {}
local foldstock = false
for i, k in pairs(eles) do
if self.AttachmentElements[k] then
table.insert(eleatts, self.AttachmentElements[k])
foldstock = foldstock or k == "foldstock"
end
end
-- Bipod bodygroup
if self:GetInBipod() and self.AttachmentElements["bipod"] then
table.insert(eleatts, self.AttachmentElements["bipod"])
end
-- Hack: Always fold stock when weapon is holstered
if IsValid(self:GetOwner()) and self:GetOwner():IsPlayer()
and self:GetOwner():GetActiveWeapon() != self and !foldstock
and self.AttachmentElements["foldstock"] then
table.insert(eleatts, self.AttachmentElements["foldstock"])
end
table.sort(eleatts, function(a, b)
return (a.SortOrder or 1) < (b.SortOrder or 1)
end)
return eleatts
end
function SWEP:DoBulletBodygroups()
self:DoBodygroups(false)
end

View File

@@ -0,0 +1,107 @@
function SWEP:DoEffects(alt)
if !IsFirstTimePredicted() then return end
local muzz_qca, muzz_qca_wm = self:GetQCAMuzzle(alt)
local data = EffectData()
data:SetEntity(self)
data:SetAttachment(muzz_qca)
data:SetHitBox(muzz_qca_wm or muzz_qca) // unused field (integer between 0-2047)
util.Effect( "TacRP_muzzleeffect", data )
end
function SWEP:GetQCAMuzzle(alt)
if self:GetValue("EffectsAlternate") then
if self:GetNthShot() % 2 == (alt and 1 or 0) then
return self:GetValue("QCA_MuzzleR"), self:GetValue("WM_QCA_MuzzleR")
else
return self:GetValue("QCA_MuzzleL"), self:GetValue("WM_QCA_MuzzleL")
end
else
return self:GetValue("QCA_Muzzle"), self:GetValue("WM_QCA_Muzzle")
end
end
function SWEP:GetQCAEject(alt)
if self:GetValue("EffectsAlternate") then
if self:GetNthShot() % 2 == (alt and 1 or 0) then
return self:GetValue("QCA_EjectR"), self:GetValue("WM_QCA_EjectR")
else
return self:GetValue("QCA_EjectL"), self:GetValue("WM_QCA_EjectL")
end
else
return self:GetValue("QCA_Eject"), self:GetValue("WM_QCA_Eject")
end
end
SWEP.EjectedShells = {}
function SWEP:DoEject(alt)
if !IsFirstTimePredicted() then return end
if self:GetValue("EjectEffect") == 0 then return end
local eject_qca, eject_qca_wm = self:GetQCAEject(alt)
local data = EffectData()
data:SetEntity(self)
data:SetFlags(self:GetValue("EjectEffect"))
data:SetAttachment(eject_qca)
data:SetHitBox(eject_qca_wm or eject_qca) // unused field (integer between 0-2047)
data:SetScale(self:GetValue("EjectScale"))
util.Effect( "TacRP_shelleffect", data )
end
function SWEP:GetTracerOrigin()
local ow = self:GetOwner()
local wm = !IsValid(ow) or !ow:IsPlayer() or !ow:GetViewModel():IsValid() or (ow != LocalPlayer() and ow != LocalPlayer():GetObserverTarget()) or (ow == LocalPlayer() and ow:ShouldDrawLocalPlayer())
local att = self:GetQCAMuzzle()
local muzz = self
if !wm then
muzz = ow:GetViewModel()
end
if muzz and muzz:IsValid() then
local posang = muzz:GetAttachment(att)
if !posang then return muzz:GetPos() end
local pos = posang.Pos
return pos
end
end
function SWEP:GetMuzzleDevice(wm)
if !wm and self:GetOwner():IsNPC() then return end
local model = self.WModel
local muzz = self
if !wm then
model = self.VModel
muzz = self:GetVM()
end
if model then
for i, k in pairs(model) do
if k.IsMuzzleDevice then
return k
end
end
end
return muzz
end
function SWEP:DrawEjectedShells()
local newshells = {}
for i, k in pairs(self.EjectedShells) do
if !k:IsValid() then continue end
k:DrawModel()
table.insert(newshells, k)
end
self.EjectedShells = newshells
end

View File

@@ -0,0 +1,116 @@
function SWEP:SwitchFiremode()
local fm = self:GetFiremode()
fm = fm + 1
if fm > #self:GetValue("Firemodes") then
fm = 1
end
-- Since pattern is firemode dependent, it has to be reset when firemode switchs
self.RecoilPatternCache = {}
self:SetFiremode(fm)
end
function SWEP:GetFiremodeAmount()
if istable(self:GetValue("Firemodes")) then
return #self:GetValue("Firemodes")
elseif self:GetValue("Firemode") == 0 then
return 0
else
return 1
end
end
function SWEP:GetNextFiremode()
if self:GetFiremodeAmount() == 0 then return 1 end
if self:GetValue("Firemodes") then
local fm = self:GetFiremode()
fm = fm + 1
if fm > #self:GetValue("Firemodes") then
fm = 1
end
return self:GetValue("Firemodes")[fm]
else
return self:GetValue("Firemode")
end
end
function SWEP:GetCurrentFiremode()
if self:GetValue("Firemodes") then
return self:GetValue("Firemodes")[self:GetFiremode()] or self:GetValue("Firemode") or 0
else
return self:GetValue("Firemode")
end
end
function SWEP:ToggleSafety(onoff)
if self:GetValue("Firemode") == 0 then return end
onoff = onoff or !self:GetSafe()
if onoff and self:DoForceSightsBehavior() then return end
if DarkRP and self:GetNWBool("TacRP_PoliceBiocode") and !self:GetOwner():isCP() then onoff = true end
self:SetSafe(onoff)
if onoff == true then
self:ToggleBlindFire(TacRP.BLINDFIRE_NONE)
self:ScopeToggle(0)
end
if CLIENT then self.LastHintLife = CurTime() end
end
local mat_1 = Material("tacrp/hud/firemode_1.png", "mips smooth")
local mat_2 = Material("tacrp/hud/firemode_2.png", "mips smooth")
local mat_3 = Material("tacrp/hud/firemode_3.png", "mips smooth")
local mat_4 = Material("tacrp/hud/firemode_4.png", "mips smooth")
local mat_a = Material("tacrp/hud/firemode_a.png", "mips smooth")
local mat_s = Material("tacrp/hud/firemode_s.png", "mips smooth")
function SWEP:GetFiremodeMat(mode)
if mode == 0 then
return mat_s
elseif mode == 1 then
return mat_1
elseif mode == 2 then
return mat_a
elseif mode == -2 then
return mat_2
elseif mode == -3 then
return mat_3
elseif mode == -4 then
return mat_4
else
return mat_1 // epic fail
end
end
function SWEP:HasFiremode(mode, base)
local valfunc = base and self.GetBaseValue or self.GetValue
if valfunc(self, "Firemodes") then
for _, v in pairs(valfunc(self, "Firemodes")) do
if v == mode or (mode < 0 and v < 0) then return true end
end
return false
else
return valfunc(self, "Firemode") == mode or (mode < 0 and valfunc(self, "Firemode") < 0)
end
end
function SWEP:GetFiremodeBurstLength(base)
local valfunc = base and self.GetBaseValue or self.GetValue
if valfunc(self, "Firemodes") then
for _, v in pairs(valfunc(self, "Firemodes")) do
if v < 0 then return -v end
end
return false
else
return valfunc(self, "Firemode") < 0 and -valfunc(self, "Firemode") or false
end
end

View File

@@ -0,0 +1,80 @@
SWEP.ClientFreeAimAng = Angle(0, 0, 0)
SWEP.ClientLastAimAngle = Angle(0, 0, 0)
function SWEP:ThinkFreeAim()
if !TacRP.ConVars["freeaim"]:GetBool() or self:GetOwner():IsBot() then return Angle(0, 0, 0) end
local eyeangles = self:GetOwner():EyeAngles()
if self:GetValue("FreeAim") then
local diff = eyeangles
if SERVER then
diff = diff - self:GetLastAimAngle()
else
diff = diff - self.ClientLastAimAngle
end
diff = LerpAngle(0.9, diff, angle_zero)
local freeaimang = Angle(self:GetFreeAimAngle())
local max = self:GetValue("FreeAimMaxAngle")
local sightdelta = self:Curve(self:GetSightDelta())
max = max * Lerp(sightdelta, 1, 0)
if self:GetBlindFireMode() > 0 then
max = max * 0.25
end
if self:GetValue("Bipod") then
local f = self:Curve(math.Clamp((CurTime() - self.LastBipodTime) / 0.25, 0, 1))
if self:GetInBipod() then
max = Lerp(f, max, 0)
else
max = Lerp(f, 0, max)
end
end
diff.p = math.NormalizeAngle(diff.p)
diff.y = math.NormalizeAngle(diff.y)
diff = diff * Lerp(sightdelta, 1, 0.25)
freeaimang.p = math.Clamp(math.NormalizeAngle(freeaimang.p) + math.NormalizeAngle(diff.p), -max, max)
freeaimang.y = math.Clamp(math.NormalizeAngle(freeaimang.y) + math.NormalizeAngle(diff.y), -max, max)
local ang2d = math.atan2(freeaimang.p, freeaimang.y)
local mag2d = math.sqrt(math.pow(freeaimang.p, 2) + math.pow(freeaimang.y, 2))
mag2d = math.min(mag2d, max)
freeaimang.p = mag2d * math.sin(ang2d)
freeaimang.y = mag2d * math.cos(ang2d)
if CLIENT then
self.ClientFreeAimAng = freeaimang
else
self:SetFreeAimAngle(freeaimang)
end
end
if SERVER then
self:SetLastAimAngle(eyeangles)
else
self.ClientLastAimAngle = eyeangles
end
end
function SWEP:GetFreeAimOffset()
if !TacRP.ConVars["freeaim"]:GetBool() or !self:GetValue("FreeAim") or self:GetOwner():IsBot() then return Angle(0, 0, 0) end
if CLIENT and LocalPlayer() == self:GetOwner() then
return self.ClientFreeAimAng
elseif CLIENT and LocalPlayer() != self:GetOwner() then
local ang = self:GetFreeAimAngle()
ang:Normalize() -- Angles are networked as unsigned or something, so normalization converts it to what we expect
return ang
else
return self:GetFreeAimAngle()
end
end

View File

@@ -0,0 +1,382 @@
function SWEP:DoDeployAnimation()
if self:GetReloading() and self:GetValue("MidReload") and !self:GetValue("ShotgunReload") and self:HasSequence("midreload") then
local t = self:PlayAnimation("midreload", self:GetValue("ReloadTimeMult"), true, true)
self:SetReloadFinishTime(CurTime() + t)
else
self:SetReloading(false)
if self:GetValue("TryUnholster") then
self:PlayAnimation("unholster", self:GetValue("DeployTimeMult") * self:GetValue("UnholsterTimeMult"), true, true)
else
-- if self:GetReady() then
-- self:PlayAnimation("unholster", self:GetValue("DeployTimeMult"), true, true)
-- else
-- self:PlayAnimation("deploy", self:GetValue("DeployTimeMult"), true, true)
-- end
self:PlayAnimation("deploy", self:GetValue("DeployTimeMult"), true, true)
end
end
end
function SWEP:Deploy()
if self:GetOwner():IsNPC() or self:GetOwner():IsNextBot() then
if SERVER then
self:NetworkWeapon()
end
if CLIENT then
self:SetupModel(true)
end
return
elseif SERVER and self:GetOwner():IsPlayer() then
self:GetOwner():SetSaveValue("m_flNextAttack", 0)
end
self:SetBaseSettings()
-- self:SetNextPrimaryFire(0)
self:SetNextSecondaryFire(0)
self:SetAnimLockTime(0)
self:SetSprintLockTime(0)
self:SetLastMeleeTime(0)
self:SetRecoilAmount(0)
self:SetLastScopeTime(0)
self:SetHolsterTime(0)
self:SetPrimedGrenade(false)
self:SetBlindFireFinishTime(0)
-- self:SetJammed(false)
self:SetCharge(false)
self:SetBurstCount(0)
self:SetScopeLevel(0)
self:SetLoadedRounds(self:Clip1())
self:SetCustomize(false)
if self:GetOwner():IsPlayer() and IsFirstTimePredicted() then
self.InversePeek = self:GetOwner():GetInfoNum("tacrp_inversepeek", 0) == 1
if !self.InversePeekInitialized then
self:SetPeeking(false)
end
self.InversePeekInitialized = true
end
self.PreviousZoom = self:GetOwner():GetCanZoom()
if IsValid(self:GetOwner()) and self:GetOwner():IsPlayer() then
self:GetOwner():SetCanZoom(false)
end
self:DoDeployAnimation()
self:GetOwner():DoAnimationEvent(ACT_HL2MP_GESTURE_RANGE_ATTACK_KNIFE)
if CLIENT then
self:SetupModel(true)
self:SetupModel(false)
self.LastHintLife = CurTime()
elseif !game.SinglePlayer() then
self:DoBodygroups(true) -- Not sure why this is necessary
self:DoBodygroups(false)
end
if (game.SinglePlayer() or CLIENT) and !TacRP.NewsPopup and TacRP.ConVars["checknews"]:GetBool() then
TacRP.NewsPopup = true
RunConsoleCommand("tacrp_news_check")
end
self:ToggleBlindFire(TacRP.BLINDFIRE_NONE)
if TacRP.ConVars["deploysafety"]:GetBool() then
self:ToggleSafety(true)
end
self:SetShouldHoldType()
if self:IsQuickNadeAllowed() then
if self:GetValue("PrimaryGrenade") then
local nade = TacRP.QuickNades[self:GetValue("PrimaryGrenade")]
if !TacRP.IsGrenadeInfiniteAmmo(nade) and self:GetOwner():GetAmmoCount(nade.Ammo) == 0 then
if SERVER then self:Remove() end
return true
end
elseif !self:CheckGrenade() then
self:SelectGrenade()
return
end
end
return true
end
local v0 = Vector(0, 0, 0)
local v1 = Vector(1, 1, 1)
local a0 = Angle(0, 0, 0)
function SWEP:ClientHolster()
if game.SinglePlayer() then
self:CallOnClient("ClientHolster")
end
local vm = self:GetVM()
if IsValid(vm) then
vm:SetSubMaterial()
vm:SetMaterial()
for i = 0, vm:GetBoneCount() do
vm:ManipulateBoneScale(i, v1)
vm:ManipulateBoneAngles(i, a0)
vm:ManipulateBonePosition(i, v0)
end
end
end
function SWEP:Holster(wep)
if game.SinglePlayer() and CLIENT then return end
if CLIENT and self:GetOwner() != LocalPlayer() then return end
if self:GetOwner():IsNPC() then
return
end
self:SetCustomize(false)
if self:GetReloading() then
if self:GetValue("ShotgunReload") then
self:SetEndReload(false)
self:SetReloading(false)
self:KillTimer("ShotgunRestoreClip")
else
self:CancelReload(false)
end
end
if self:GetHolsterTime() > CurTime() then return false end -- or self:GetPrimedGrenade()
if !TacRP.ConVars["holster"]:GetBool() or (self:GetHolsterTime() != 0 and self:GetHolsterTime() <= CurTime()) or !IsValid(wep) then
-- Do the final holster request
-- Picking up props try to switch to NULL, by the way
self:SetHolsterTime(0)
self:SetHolsterEntity(NULL)
self:SetReloadFinishTime(0)
local holster = self:GetValue("HolsterVisible")
if SERVER and holster then
net.Start("TacRP_updateholster")
net.WriteEntity(self:GetOwner())
net.WriteEntity(self)
net.Broadcast()
end
if game.SinglePlayer() then
self:CallOnClient("KillModel")
else
if CLIENT then
self:RemoveCustomizeHUD()
self:KillModel()
end
end
if self.PreviousZoom then
self:GetOwner():SetCanZoom(true)
end
self:ClientHolster()
return true
else
local reverse = 1
local anim = "holster"
if self:GetValue("NoHolsterAnimation") then
anim = "deploy"
reverse = -1
end
local animation = self:PlayAnimation(anim, self:GetValue("HolsterTimeMult") * reverse, true, true)
self:SetHolsterTime(CurTime() + (animation or 0))
self:SetHolsterEntity(wep)
self:SetScopeLevel(0)
self:KillTimers()
self:ToggleBlindFire(TacRP.BLINDFIRE_NONE)
self:GetOwner():SetFOV(0, 0.1)
self:SetLastProceduralFireTime(0)
self:GetOwner():DoAnimationEvent(ACT_HL2MP_GESTURE_RANGE_ATTACK_SLAM)
self:SetShouldHoldType()
end
end
local holsteranticrash = false
hook.Add("StartCommand", "TacRP_Holster", function(ply, ucmd)
local wep = ply:GetActiveWeapon()
if IsValid(wep) and wep.ArcticTacRP and wep:GetHolsterTime() != 0 and wep:GetHolsterTime() - wep:GetPingOffsetScale() <= CurTime() and IsValid(wep:GetHolsterEntity()) then
wep:SetHolsterTime(-math.huge) -- Pretty much force it to work
if !holsteranticrash then
holsteranticrash = true
ucmd:SelectWeapon(wep:GetHolsterEntity()) -- Call the final holster request
holsteranticrash = false
end
end
end)
function SWEP:Initialize()
self:SetShouldHoldType()
self:SetBaseSettings()
self:SetLastMeleeTime(0)
self:SetNthShot(0)
if self:GetOwner():IsNPC() then
self:NPC_Initialize()
return
end
if self:GetOwner():IsNextBot() then
return
end
self.m_WeaponDeploySpeed = 4
if engine.ActiveGamemode() == "terrortown" then
self:TTT_Init()
end
self:ClientInitialize()
if SERVER and engine.ActiveGamemode() != "terrortown" then
-- If we have any pre-existing attachments, network it
local empty = true
for slot, slottbl in pairs(self.Attachments) do
if slottbl.Installed then empty = false break end
end
if !empty then
self:NetworkWeapon()
end
end
end
function SWEP:ClientInitialize()
if SERVER then return end
if game.SinglePlayer() and SERVER and IsValid(self:GetOwner()) and self:GetOwner():IsPlayer() then
self:CallOnClient("ClientInitialize")
end
if !LocalPlayer().TacRPGreet and !TacRP.ConVars["shutup"]:GetBool() then
LocalPlayer().TacRPGreet = true
end
-- local mat = Material("entities/" .. self:GetClass() .. ".png")
-- local tex = mat:GetTexture("$basetexture")
-- killicon.Add(self:GetClass(), tex:GetName(), Color( 255, 255, 255, 255 ) )
end
function SWEP:SetBaseSettings()
if game.SinglePlayer() and SERVER and IsValid(self:GetOwner()) and self:GetOwner():IsPlayer() then
self:CallOnClient("SetBaseSettings")
end
local fm = self:GetCurrentFiremode()
if fm != 1 then
if self:GetValue("RunawayBurst") and fm < 0 and !self:GetValue("AutoBurst") then
self.Primary.Automatic = false
else
self.Primary.Automatic = true
end
else
self.Primary.Automatic = false
end
if self.PrimaryGrenade then
self.Primary.ClipSize = -1
self.Primary.Ammo = TacRP.QuickNades[self.PrimaryGrenade].Ammo or ""
self.Primary.DefaultClip = 1
else
self.Primary.ClipSize = self:GetCapacity()
self.Primary.Ammo = self:GetAmmoType()
self.Primary.DefaultClip = math.ceil(self.Primary.ClipSize * TacRP.ConVars["defaultammo"]:GetFloat())
end
if self:IsQuickNadeAllowed() then
self.Secondary.Ammo = self:GetGrenade().Ammo or "grenade"
else
self.Secondary.Ammo = "none"
end
if SERVER and IsValid(self:GetOwner()) and self:GetOwner():IsPlayer() and self:GetCapacity() > 0 and self:Clip1() > self:GetCapacity() then
self:GetOwner():GiveAmmo(self:Clip1() - self:GetCapacity(), self:GetAmmoType())
self:SetClip1(self:GetCapacity())
end
end
function SWEP:SetShouldHoldType()
if self:GetOwner():IsNPC() and !self:GetOwner():IsNextBot() then
self:SetHoldType(self:GetValue("HoldTypeNPC") or self:GetValue("HoldType"))
return
end
if self:GetHolsterTime() > CurTime() then
self:SetHoldType("passive")
return
end
if (self:GetIsSprinting() or self:ShouldLowerWeapon() or self:GetSafe()) and self:GetValue("HoldTypeSprint") then
self:SetHoldType(self:GetValue("HoldTypeSprint"))
return
end
if self:GetBlindFire() then
if self:GetBlindFireMode() == TacRP.BLINDFIRE_KYS and self:GetValue("HoldTypeSuicide") then
self:SetHoldType(self:GetValue("HoldTypeSuicide"))
return
elseif self:GetValue("HoldTypeBlindFire") then
self:SetHoldType(self:GetValue("HoldTypeBlindFire"))
return
end
elseif self:GetScopeLevel() > 0 and self:GetValue("HoldTypeSighted") then
self:SetHoldType(self:GetValue("HoldTypeSighted"))
return
elseif self:GetScopeLevel() > 0 and TacRP.HoldTypeSightedLookup[self:GetValue("HoldType")] then
self:SetHoldType(TacRP.HoldTypeSightedLookup[self:GetValue("HoldType")])
return
end
if self:GetCustomize() and self:GetValue("HoldTypeCustomize") then
self:SetHoldType(self:GetValue("HoldTypeCustomize"))
return
end
self:SetHoldType(self:GetValue("HoldType"))
end
function SWEP:OnRemove()
if IsValid(self:GetOwner()) and self:GetOwner():IsPlayer() then
self:ToggleBoneMods(TacRP.BLINDFIRE_NONE)
if CLIENT then
local vm = self:GetOwner():GetViewModel()
if IsValid(vm) then
vm:SetMaterial() -- Quick and dirty fix for grenade materials persisting on VM when stripped
end
end
end
if CLIENT and (self:GetCustomize() or (self.GrenadeMenuAlpha or 0) > 0 or (self.BlindFireMenuAlpha or 0) > 0) then
gui.EnableScreenClicker(false)
TacRP.CursorEnabled = false
end
end
function SWEP:EquipAmmo(ply)
local ammotype = self.Primary.Ammo
if ammotype == "" then return end
local supplyamount = self.GaveDefaultAmmo and self:Clip1() or math.ceil(math.max(1, self.Primary.ClipSize) * TacRP.ConVars["defaultammo"]:GetFloat())
ply:GiveAmmo(supplyamount, ammotype)
end

View File

@@ -0,0 +1,242 @@
SWEP.Sound_MeleeHit = nil
SWEP.Sound_MeleeHitBody = nil
-- Don't you love lua table inheritance??
SWEP._Sound_MeleeHit = {
"TacRP/weapons/melee_hit-1.wav",
"TacRP/weapons/melee_hit-2.wav"
}
SWEP._Sound_MeleeHitBody = {
"TacRP/weapons/melee_body_hit-1.wav",
"TacRP/weapons/melee_body_hit-2.wav",
"TacRP/weapons/melee_body_hit-3.wav",
"TacRP/weapons/melee_body_hit-4.wav",
"TacRP/weapons/melee_body_hit-5.wav",
}
function SWEP:Melee(alt)
if !self:GetValue("CanMeleeAttack") then return end
if self:StillWaiting(false, true) then return end
if DarkRP and self:GetNWBool("TacRP_PoliceBiocode") and !self:GetOwner():isCP() then return end
-- if self:SprintLock() then return end
self.Primary.Automatic = true
self.Secondary.Automatic = true
self:SetCharge(false)
self:CancelReload()
self:ToggleBlindFire(TacRP.BLINDFIRE_NONE)
self:ScopeToggle(0)
local dmg = self:GetValue("MeleeDamage") * self:GetConfigDamageMultiplier()
local range = self:GetValue("MeleeRange")
local delay = self:GetValue("MeleeDelay")
if alt then
self:PlayAnimation("melee2", 1, false, true)
-- self:GetOwner():DoAnimationEvent(self:GetValue("GestureBash2") or self:GetValue("GestureBash"))
-- range = self:GetValue("Melee2Range") or range
dmg = self:GetHeavyAttackDamage() * self:GetConfigDamageMultiplier()
else
self:PlayAnimation("melee", 1, false, true)
-- self:GetOwner():DoAnimationEvent(self:GetValue("GestureBash"))
end
local t = alt and self:GetHeavyAttackTime() or self:GetValue("MeleeAttackTime")
self:GetOwner():DoCustomAnimEvent(PLAYERANIMEVENT_ATTACK_PRIMARY, t * 1000 * (alt and -1 or 1))
if delay > 0 then
self:EmitSound(self:ChooseSound(self:GetValue("Sound_MeleeSwing")), 75, 100, 1)
end
self:SetTimer(delay, function()
self:GetOwner():LagCompensation(true)
local filter = {self:GetOwner()}
table.Add(filter, self.Shields)
local start = self:GetOwner():GetShootPos()
local dir = self:GetOwner():GetAimVector()
local tr = util.TraceLine({
start = start,
endpos = start + dir * range,
filter = filter,
mask = MASK_SHOT_HULL,
})
-- weapon_hl2mpbasebasebludgeon.cpp: do a hull trace if not hit
if tr.Fraction == 1 or !IsValid(tr.Entity) then
local dim = 32
local pos2 = tr.HitPos - dir * (dim * 1.732)
local tr2 = util.TraceHull({
start = start,
endpos = pos2,
filter = filter,
mask = MASK_SHOT_HULL,
mins = Vector(-dim, -dim, -dim),
maxs = Vector(dim, dim, dim)
})
if tr2.Fraction < 1 and IsValid(tr2.Entity) then
local dot = (tr2.Entity:GetPos() - start):GetNormalized():Dot(dir)
if dot >= 0.5 then
tr = tr2
end
end
end
local dmginfo = DamageInfo()
dmginfo:SetDamage(dmg)
dmginfo:SetDamageForce(dir * dmg * 500)
dmginfo:SetDamagePosition(tr.HitPos)
dmginfo:SetDamageType(self:GetValue("MeleeDamageType"))
if dmginfo:GetDamageType() == DMG_GENERIC and engine.ActiveGamemode() == "terrortown" then
dmginfo:SetDamageType(DMG_CLUB) -- use CLUB so TTT can assign DNA (it does not leave DNA on generic damage)
end
dmginfo:SetAttacker(self:GetOwner())
dmginfo:SetInflictor(self)
if tr.Fraction < 1 then
TacRP.CancelBodyDamage(tr.Entity, dmginfo, tr.HitGroup)
if IsValid(tr.Entity) and (tr.Entity:IsNPC() or tr.Entity:IsPlayer() or tr.Entity:IsNextBot() or tr.Entity:IsRagdoll()) then
self:EmitSound(self:ChooseSound(self:GetValue("Sound_MeleeHitBody") or self:GetValue("_Sound_MeleeHitBody")), 75, 100, 1, CHAN_ITEM)
if !tr.Entity:IsRagdoll() and self:GetValue("MeleeBackstab") then
local ang = math.NormalizeAngle(self:GetOwner():GetAngles().y - tr.Entity:GetAngles().y)
if ang <= 60 and ang >= -60 then
dmginfo:ScaleDamage(self:GetValue("MeleeBackstabMult"))
self:EmitSound("tacrp/riki_backstab.wav", 70, 100, 0.4)
end
end
else
self:EmitSound(self:ChooseSound(self:GetValue("Sound_MeleeHit") or self:GetValue("_Sound_MeleeHit")), 75, 100, 1, CHAN_ITEM)
end
if IsValid(tr.Entity) and self:GetValue("MeleeSlow") then
tr.Entity.TacRPBashSlow = true
end
if tr.HitGroup == HITGROUP_HEAD then
dmginfo:ScaleDamage(1.25)
end
if IsValid(tr.Entity) then
if tr.Entity.LVS then return end
--tr.Entity:TakeDamageInfo(dmginfo)
tr.Entity:DispatchTraceAttack(dmginfo, tr)
end
self:FireBullets({
Attacker = self:GetOwner(),
Damage = 0,
Force = 0,
Distance = range + 8,
HullSize = 0,
Tracer = 0,
Dir = (tr.HitPos - start):GetNormalized(),
Src = start,
})
else
local tmiss
if !alt and self:GetValue("MeleeAttackMissTime") then
tmiss = self:GetValue("MeleeAttackMissTime")
elseif alt then
tmiss = self:GetHeavyAttackTime(true, false)
end
if tmiss then
self:SetNextSecondaryFire(CurTime() + (tmiss - delay))
end
if delay == 0 then
self:EmitSound(self:ChooseSound(self:GetValue("Sound_MeleeSwing")), 75, 100, 1)
end
end
self:GetOwner():LagCompensation(false)
end, "Melee")
self:SetLastMeleeTime(CurTime())
self:SetNextSecondaryFire(CurTime() + t)
end
function SWEP:GetHeavyAttackDamage(base)
local valfunc = base and self.GetBaseValue or self.GetValue
return valfunc(self, "Melee2Damage") or valfunc(self, "MeleeDamage") * self:GetMeleePerkDamage(base) * 1.5
end
function SWEP:GetHeavyAttackTime(miss, base)
local valfunc = base and self.GetBaseValue or self.GetValue
if miss then
return (valfunc(self, "Melee2AttackMissTime") or (valfunc(self, "MeleeAttackMissTime") * 1.6))
* self:GetMeleePerkCooldown(base)
else
return (valfunc(self, "Melee2AttackTime") or (valfunc(self, "MeleeAttackTime") * 1.6))
* self:GetMeleePerkCooldown(base)
end
end
function SWEP:GetMeleePerkDamage(base)
local valfunc = base and self.GetBaseValue or self.GetValue
local stat = valfunc(self, "MeleePerkStr")
if stat >= 0.5 then
return Lerp((stat - 0.5) * 2, 1, 2)
else
return Lerp(stat * 2, 0.7, 1)
end
end
function SWEP:GetMeleePerkCooldown(base)
local valfunc = base and self.GetBaseValue or self.GetValue
local stat = valfunc(self, "MeleePerkAgi")
if stat >= 0.5 then
return Lerp((stat - 0.5) * 2, 1, 0.7)
else
return Lerp(stat * 2, 1.3, 1)
end
end
function SWEP:GetMeleePerkSpeed(base)
local valfunc = base and self.GetBaseValue or self.GetValue
local stat = valfunc(self, "MeleePerkAgi")
if stat >= 0.5 then
return Lerp((stat - 0.5) * 2, 1, 1.5)
else
return Lerp(stat * 2, 0.5, 1)
end
end
function SWEP:GetMeleePerkVelocity(base)
local valfunc = base and self.GetBaseValue or self.GetValue
local stat = valfunc(self, "MeleePerkInt")
if stat >= 0.5 then
return Lerp((stat - 0.5) * 2, 1, 3) * valfunc(self, "MeleeThrowForce")
else
return Lerp(stat * 2, 0.5, 1) * valfunc(self, "MeleeThrowForce")
end
end
hook.Add("PostEntityTakeDamage", "tacrp_melee", function(ent, dmg, took)
if ent.TacRPBashSlow then
if took and (!ent:IsPlayer() or (ent:IsPlayer() and !(IsValid(ent:GetActiveWeapon()) and ent:GetActiveWeapon().ArcticTacRP and ent:GetActiveWeapon():GetValue("StunResist")))) then
ent:SetNWFloat("TacRPLastBashed", CurTime())
end
ent.TacRPBashSlow = false
end
local wep = dmg:GetInflictor()
if (!IsValid(wep) or !wep:IsWeapon()) and IsValid(dmg:GetAttacker()) and dmg:GetAttacker():IsPlayer() then wep = dmg:GetAttacker():GetActiveWeapon() end
if took and (ent:IsPlayer() or ent:IsNPC() or ent:IsNextBot()) and IsValid(wep) and wep.ArcticTacRP then
if (wep:GetValue("Lifesteal") or 0) > 0 then
wep:GetOwner():SetHealth(math.min(math.max(wep:GetOwner():GetMaxHealth(), wep:GetOwner():Health()),
wep:GetOwner():Health() + dmg:GetDamage() * wep:GetValue("Lifesteal")))
end
if (wep:GetValue("DamageCharge") or 0) > 0 then
wep:SetBreath(math.min(1, wep:GetBreath() + dmg:GetDamage() * wep:GetValue("DamageCharge")))
end
end
end)

View File

@@ -0,0 +1,187 @@
function SWEP:NPC_PrimaryAttack()
if !IsValid(self:GetOwner()) then return end
local enemy = self:GetOwner():GetEnemy()
local aps = self:GetValue("AmmoPerShot")
if self:Clip1() < aps then
if !IsValid(enemy) or !IsValid(enemy:GetActiveWeapon()) or table.HasValue({"weapon_crowbar", "weapon_stunstick"}, enemy:GetActiveWeapon():GetClass()) then
// do not attempt to find cover if enemy does not have a ranged weapon
self:GetOwner():SetSchedule(SCHED_RELOAD)
else
self:GetOwner():SetSchedule(SCHED_HIDE_AND_RELOAD)
end
return
end
self:SetBaseSettings()
self:SetShouldHoldType()
self.Primary.Automatic = true
local pvar = self:GetValue("ShootPitchVariance")
local sshoot = self:GetValue("Sound_Shoot")
if self:GetValue("Silencer") then
sshoot = self:GetValue("Sound_Shoot_Silenced")
end
if istable(sshoot) then
sshoot = table.Random(sshoot)
end
self:EmitSound(sshoot, self:GetValue("Vol_Shoot"), self:GetValue("Pitch_Shoot") + math.Rand(-pvar, pvar), 1, CHAN_WEAPON)
self:SetClip1(self:Clip1() - aps)
local delay = 60 / self:GetValue("RPM")
self:SetNextPrimaryFire(CurTime() + delay)
if delay < 0.1 then
self:GetOwner():NextThink(CurTime() + delay) // they will only attempt to fire once per think
end
local spread = self:GetNPCSpread()
local dir = self:GetOwner():GetAimVector()
if self:GetValue("ShootEnt") then
if IsValid(enemy) then
dir = (enemy:WorldSpaceCenter() - self:GetOwner():GetShootPos()):GetNormalized():Angle()
dir = dir + ((spread + (0.1 / self:GetOwner():GetCurrentWeaponProficiency())) * AngleRand() / 3.6)
end
self:ShootRocket(dir)
else
self:GetOwner():FireBullets({
Damage = self:GetValue("Damage_Max"),
Force = 8,
TracerName = "tacrp_tracer",
Tracer = self:GetValue("TracerNum"),
Num = self:GetValue("Num"),
Dir = dir,
Src = self:GetOwner():GetShootPos(),
Spread = Vector(spread, spread, spread),
Callback = function(att, btr, dmg)
local range = (btr.HitPos - btr.StartPos):Length()
self:AfterShotFunction(btr, dmg, range, 0, {}) // self:GetValue("Penetration")
if TacRP.Developer() then
if SERVER then
debugoverlay.Cross(btr.HitPos, 4, 5, Color(255, 0, 0), false)
else
debugoverlay.Cross(btr.HitPos, 4, 5, Color(255, 255, 255), false)
end
end
end
})
end
self:DoEffects()
self:DoEject()
end
function SWEP:GetNPCBulletSpread(prof)
local mode = self:GetCurrentFiremode()
if mode < 0 then
return 10 / (prof + 1)
elseif mode == 1 then
if math.Rand(0, 100) < (prof + 5) * 5 then
return 2 / (prof + 1)
else
return 20 / (prof + 1)
end
elseif mode > 1 then
if math.Rand(0, 100) < (prof + 5) * 2 then
return 5 / (prof + 1)
else
return 30 / (prof + 1)
end
end
return 15
end
function SWEP:GetNPCSpread()
return self:GetValue("Spread")
end
function SWEP:GetNPCBurstSettings()
local mode = self:GetCurrentFiremode()
local delay = 60 / self:GetValue("RPM")
if !mode then return 1, 1, delay end
if mode < 0 then
return -mode, -mode, delay
elseif mode == 0 then
return 0, 0, delay
elseif mode == 1 then
local c = self:GetCapacity()
return math.ceil(c * 0.075), math.max(1, math.floor(c * math.Rand(0.15, 0.3))), delay + math.Rand(0.1, 0.2)
elseif mode >= 2 then
return math.min(self:Clip1(), 1 + math.floor(0.5 / delay)), math.min(self:Clip1(), 1 + math.floor(2 / delay)), delay
end
end
function SWEP:GetNPCRestTimes()
local mode = self:GetCurrentFiremode()
local postburst = self:GetValue("PostBurstDelay") or 0
local m = self:GetValue("RecoilKick")
local delay = 60 / self:GetValue("RPM")
if !mode then return delay + 0.3, delay + 0.6 end
local o = m > 1 and math.sqrt(m) or m
if delay <= 60 / 90 then
return delay + 0.1 * o, delay + 0.2 * o
elseif mode < 0 then
o = delay + o * 0.5 + postburst
end
return delay + 0.4 * o, delay + 0.6 * o
end
function SWEP:CanBePickedUpByNPCs()
return self.NPCUsable
end
function SWEP:NPC_Reload()
self:DropMagazine()
end
function SWEP:NPC_Initialize()
if CLIENT then return end
// auto attachment
if TacRP.ConVars["npc_atts"]:GetBool() then
for i, slot in pairs(self.Attachments) do
local atts = TacRP.GetAttsForCats(slot.Category or "", self)
local ind = math.random(0, #atts)
if ind > 0 and math.random() <= 0.75 then
slot.Installed = atts[ind]
end
end
self:InvalidateCache()
end
timer.Simple(0.25, function()
if !IsValid(self) then return end
self:NetworkWeapon()
end)
self:SetBaseSettings()
self:SetClip1(self:GetCapacity())
if math.random() <= 0.5 then
self:SetFiremode(math.random(1, self:GetFiremodeAmount()))
end
end

View File

@@ -0,0 +1,139 @@
local function draw_debug()
return (CLIENT or game.SinglePlayer()) and TacRP.Developer(2)
end
local function IsPenetrating(ptr, ptrent)
if ptrent:IsWorld() then
return ptr.Contents != CONTENTS_EMPTY
elseif IsValid(ptrent) then
local withinbounding = false
local hboxset = ptrent:GetHitboxSet()
local hitbone = ptrent:GetHitBoxBone(ptr.HitBox, hboxset)
if hitbone then
-- If we hit a hitbox, compare against that hitbox only
local mins, maxs = ptrent:GetHitBoxBounds(ptr.HitBox, hboxset)
local bonepos, boneang = ptrent:GetBonePosition(hitbone)
mins = mins * 1.1
maxs = maxs * 1.1
local lpos = WorldToLocal(ptr.HitPos, ptr.HitNormal:Angle(), bonepos, boneang)
withinbounding = lpos:WithinAABox(mins, maxs)
if draw_debug() then
debugoverlay.BoxAngles(bonepos, mins, maxs, boneang, 5, Color(255, 255, 255, 10))
end
elseif util.PointContents(ptr.HitPos) != CONTENTS_EMPTY then
-- Otherwise default to rotated OBB
local mins, maxs = ptrent:OBBMins(), ptrent:OBBMaxs()
withinbounding = ptrent:WorldToLocal(ptr.HitPos):WithinAABox(mins, maxs)
if draw_debug() then
debugoverlay.BoxAngles(ptrent:GetPos(), mins, maxs, ptrent:GetAngles(), 5, Color(255, 255, 255, 10))
end
end
if draw_debug() then
debugoverlay.Cross(ptr.HitPos, withinbounding and 4 or 6, 5, withinbounding and Color(255, 255, 0) or Color(128, 255, 0), true)
end
return withinbounding
end
return false
end
function SWEP:Penetrate(tr, range, penleft, alreadypenned)
if !TacRP.ConVars["penetration"]:GetBool() then return end
if !IsValid(self:GetOwner()) then return end
local hitpos, startpos = tr.HitPos, tr.StartPos
local dir = (hitpos - startpos):GetNormalized()
if tr.HitSky then return end
if penleft <= 0 then return end
alreadypenned = alreadypenned or {}
local skip = false
local trent = tr.Entity
local penmult = TacRP.PenTable[tr.MatType] or 1
local pentracelen = math.max(penleft * penmult / 2, 2)
local curr_ent = trent
if !tr.HitWorld then penmult = penmult * 0.5 end
if trent.Impenetrable then penmult = 100000 end
if trent.mmRHAe then penmult = trent.mmRHAe end
-- penmult = penmult * math.Rand(0.9, 1.1) * math.Rand(0.9, 1.1)
local endpos = hitpos
local td = {}
td.start = endpos
td.endpos = endpos + (dir * pentracelen)
td.mask = MASK_SHOT
local ptr = util.TraceLine(td)
local ptrent = ptr.Entity
while !skip and penleft > 0 and IsPenetrating(ptr, ptrent) and ptr.Fraction < 1 and ptrent == curr_ent do
penleft = penleft - (pentracelen * penmult)
td.start = endpos
td.endpos = endpos + (dir * pentracelen)
td.mask = MASK_SHOT
ptr = util.TraceLine(td)
if TacRP.Developer() then
local pdeltap = penleft / self:GetValue("Penetration")
local colorlr = Lerp(pdeltap, 0, 255)
debugoverlay.Line(endpos, endpos + (dir * pentracelen), 10, Color(255, colorlr, colorlr), true)
end
endpos = endpos + (dir * pentracelen)
range = range + pentracelen
ptrent = ptr.Entity
end
if penleft > 0 then
if (dir:Length() == 0) then return end
self:GetOwner():FireBullets({
Damage = self:GetValue("Damage_Max"),
Force = 4,
Tracer = 0,
Num = 1,
Dir = dir,
Src = endpos,
Callback = function(att, btr, dmg)
range = range + (btr.HitPos - btr.StartPos):Length()
self:AfterShotFunction(btr, dmg, range, penleft, alreadypenned)
if TacRP.Developer() then
if SERVER then
debugoverlay.Cross(btr.HitPos, 4, 5, Color(255, 0, 0), false)
else
debugoverlay.Cross(btr.HitPos, 4, 5, Color(255, 255, 255), false)
end
end
end
})
self:GetOwner():FireBullets({
Damage = 0,
Force = 0,
Tracer = 0,
Num = 1,
Distance = 1,
Dir = -dir,
Src = endpos,
})
end
end

View File

@@ -0,0 +1,347 @@
SWEP.GrenadeDownKey = IN_GRENADE1
SWEP.GrenadeMenuKey = IN_GRENADE2
function SWEP:IsQuickNadeAllowed()
return TacRP.ConVars["quicknade"]:GetBool() and self:GetValue("CanQuickNade")
end
function SWEP:PrimeGrenade()
self.Primary.Automatic = true
if !self:IsQuickNadeAllowed() and !self:GetValue("PrimaryGrenade") then return end
if self:StillWaiting(nil, true) then return end
if self:GetPrimedGrenade() then return end
if engine.ActiveGamemode() == "terrortown" and GetRoundState() == ROUND_PREP and ((TTT2 and !GetConVar("ttt_nade_throw_during_prep"):GetBool()) or (!TTT2 and GetConVar("ttt_no_nade_throw_during_prep"):GetBool())) then
return
end
if !self:GetValue("PrimaryGrenade") and !self:CheckGrenade(nil, true) then
self:SelectGrenade(nil, true)
end
-- if self:SprintLock() then return end
self:CancelReload()
local nade = self:GetValue("PrimaryGrenade") and TacRP.QuickNades[self:GetValue("PrimaryGrenade")] or self:GetGrenade()
if nade.Singleton then
if !self:GetOwner():HasWeapon(nade.GrenadeWep) then return end
elseif !TacRP.IsGrenadeInfiniteAmmo(nade) then
local ammo = self:GetOwner():GetAmmoCount(nade.Ammo)
if ammo < 1 then return end
-- self:GetOwner():SetAmmo(ammo - 1, nade.Ammo)
end
local rate = self:GetValue("QuickNadeTimeMult") / (nade.ThrowSpeed or 1)
if self:GetValue("QuickNadeTryImpact") and nade.CanSetImpact then
rate = rate * 1.5
end
local t = self:PlayAnimation("prime_grenade", rate, true)
self:SetPrimedGrenade(true)
self:ToggleBlindFire(TacRP.BLINDFIRE_NONE)
self:ScopeToggle(0)
local ct = CurTime()
self:SetStartPrimedGrenadeTime(ct)
self:SetAnimLockTime(ct + (t * 0.75))
self:SetNextPrimaryFire(ct + (t * 1.1))
self:GetOwner():DoCustomAnimEvent(PLAYERANIMEVENT_ATTACK_SECONDARY, t * 1000)
if !nade.NoSounds then
self:EmitSound(nade.PullSound or ("TacRP/weapons/grenade/pullpin-" .. math.random(1, 2) .. ".wav"), 65)
end
if CLIENT then return end
self.CurrentGrenade = self:GetGrenade()
end
function SWEP:ThrowGrenade()
local nade = self:GetValue("PrimaryGrenade") and TacRP.QuickNades[self:GetValue("PrimaryGrenade")] or self.CurrentGrenade or self:GetGrenade()
local force = nade.ThrowForce
local ent = nade.GrenadeEnt
local src = self:GetOwner():EyePos()
local ang = self:GetOwner():EyeAngles()
local spread = 0
local amount = 1
local t = 0
if !nade.OverhandOnly and (self.GrenadeThrowOverride == true or (self.GrenadeThrowOverride == nil and !self:GetOwner():KeyDown(self.GrenadeDownKey))) then
t = self:PlayAnimation("throw_grenade_underhand", self:GetValue("QuickNadeTimeMult"), true, true)
force = force / 2
ang:RotateAroundAxis(ang:Right(), 20)
if nade.UnderhandSpecial then
force = force * 0.75
ang:RotateAroundAxis(ang:Right(), -10)
amount = math.random(2, 4)
spread = 0.15
end
else
ang:RotateAroundAxis(ang:Right(), 5)
t = self:PlayAnimation("throw_grenade", self:GetValue("QuickNadeTimeMult"), true, true)
end
self.GrenadeThrowOverride = nil
self.GrenadeDownKey = IN_GRENADE1
if SERVER then
if (self.GrenadeThrowCharge or 0) > 0 then
force = force * (1 + self.GrenadeThrowCharge)
end
self.GrenadeThrowCharge = nil
for i = 1, amount do
local rocket = ents.Create(ent or "")
if !IsValid(rocket) then return end
local dispersion = Angle(math.Rand(-1, 1), math.Rand(-1, 1), 0)
dispersion = dispersion * spread * 36
rocket:SetPos(src)
rocket:SetOwner(self:GetOwner())
rocket:SetAngles(ang + dispersion)
rocket:Spawn()
rocket:SetPhysicsAttacker(self:GetOwner(), 10)
if TacRP.IsGrenadeInfiniteAmmo(nade) then
rocket.PickupAmmo = nil
rocket.WeaponClass = nil -- dz ents
end
if self:GetValue("QuickNadeTryImpact") and nade.CanSetImpact then
rocket.InstantFuse = false
rocket.Delay = 0
rocket.Armed = false
rocket.ImpactFuse = true
end
if nade.TTTTimer then
rocket:SetGravity(0.4)
rocket:SetFriction(0.2)
rocket:SetElasticity(0.45)
rocket:SetDetonateExact(CurTime() + nade.TTTTimer)
rocket:SetThrower(self:GetOwner())
end
local phys = rocket:GetPhysicsObject()
if phys:IsValid() then
phys:ApplyForceCenter((ang + dispersion):Forward() * force + self:GetOwner():GetVelocity())
phys:AddAngleVelocity(VectorRand() * 1000)
end
if nade.Spoon and TacRP.ConVars["dropmagazinemodel"]:GetBool() then
local mag = ents.Create("TacRP_droppedmag")
if mag then
mag:SetPos(src)
mag:SetAngles(ang)
mag.Model = "models/weapons/tacint/flashbang_spoon.mdl"
mag.ImpactType = "spoon"
mag:SetOwner(self:GetOwner())
mag:Spawn()
local phys2 = mag:GetPhysicsObject()
if IsValid(phys2) then
phys2:ApplyForceCenter(ang:Forward() * force * 0.25 + VectorRand() * 25)
phys2:AddAngleVelocity(Vector(math.Rand(-300, 300), math.Rand(-300, 300), math.Rand(-300, 300)))
end
end
end
end
if !nade.NoSounds then
self:EmitSound(nade.ThrowSound or ("tacrp/weapons/grenade/throw-" .. math.random(1, 2) .. ".wav"), 65)
end
if !nade.Singleton and !TacRP.IsGrenadeInfiniteAmmo(nade) then
self:GetOwner():RemoveAmmo(1, nade.Ammo)
end
end
if self:GetValue("PrimaryGrenade") then
if !TacRP.IsGrenadeInfiniteAmmo(nade) and self:GetOwner():GetAmmoCount(nade.Ammo) == 0 then
if SERVER then
self:Remove()
end
else
self:SetTimer(t, function()
self:PlayAnimation("deploy", self:GetValue("DeployTimeMult"), true, true)
end)
end
elseif nade.Singleton and self:GetOwner():HasWeapon(nade.GrenadeWep) then
local nadewep = self:GetOwner():GetWeapon(nade.GrenadeWep)
nadewep.OnRemove = nil -- TTT wants to switch to unarmed when the nade wep is removed - DON'T.
if SERVER then
nadewep:Remove()
end
elseif nade.GrenadeWep and self:GetOwner():HasWeapon(nade.GrenadeWep) and !TacRP.IsGrenadeInfiniteAmmo(nade) and self:GetOwner():GetAmmoCount(nade.Ammo) == 0 then
if SERVER then
self:GetOwner():GetWeapon(nade.GrenadeWep):Remove()
end
end
end
function SWEP:GetGrenade(index)
index = index or self:GetGrenadeIndex()
return TacRP.QuickNades[TacRP.QuickNades_Index[index]]
end
function SWEP:GetGrenadeIndex()
return IsValid(self:GetOwner()) and self:GetOwner():GetNWInt("ti_nade", 1) or 1
end
function SWEP:GetNextGrenade(ind)
ind = ind or self:GetGrenadeIndex()
ind = ind + 1
if ind > TacRP.QuickNades_Count then
ind = 1
elseif ind < 1 then
ind = TacRP.QuickNades_Count
end
if !self:CheckGrenade(ind) then
return self:GetNextGrenade(ind)
end
return self:GetGrenade(ind)
end
function SWEP:SelectGrenade(index, requireammo)
if !self:IsQuickNadeAllowed() then return end
if !IsFirstTimePredicted() then return end
if self:GetPrimedGrenade() then return end
local ind = self:GetOwner():GetNWInt("ti_nade", 1)
if index then
ind = index
elseif !requireammo then
if self:GetOwner():KeyDown(IN_WALK) then
ind = ind - 1
else
ind = ind + 1
end
end
if ind > TacRP.QuickNades_Count then
ind = 1
elseif ind < 1 then
ind = TacRP.QuickNades_Count
end
if !self:CheckGrenade(ind, requireammo) then
local nades = self:GetAvailableGrenades(requireammo)
if #nades > 0 then
ind = nades[1].Index
end
end
self:GetOwner():SetNWInt("ti_nade", ind)
self.Secondary.Ammo = self:GetGrenade().Ammo or "none"
end
function SWEP:CheckGrenade(index, checkammo)
index = index or (self:GetValue("PrimaryGrenade") and TacRP.QuickNades_Index[self:GetValue("PrimaryGrenade")] or self:GetOwner():GetNWInt("ti_nade", 1))
local nade = self:GetGrenade(index)
if nade.Singleton then
return self:GetOwner():HasWeapon(nade.GrenadeWep)
end
local hasammo = (nade.Ammo == nil or self:GetOwner():GetAmmoCount(nade.Ammo) > 0)
if (nade.Secret and !hasammo and (!nade.SecretWeapon or !self:GetOwner():HasWeapon(nade.SecretWeapon))) or (nade.RequireStat and !self:GetValue(nade.RequireStat)) then
return false
end
if checkammo and !TacRP.IsGrenadeInfiniteAmmo(index) and !hasammo then
return false
end
return true
end
function SWEP:GetAvailableGrenades(checkammo)
local nades = {}
for i = 1, TacRP.QuickNades_Count do
if self:CheckGrenade(i, checkammo) then
table.insert(nades, self:GetGrenade(i))
end
end
return nades
end
if CLIENT then
SWEP.QuickNadeModel = nil
end
function SWEP:ThinkGrenade()
if !self:IsQuickNadeAllowed() then return end
if CLIENT then
if self:GetPrimedGrenade() and !IsValid(self.QuickNadeModel) and self:GetStartPrimedGrenadeTime() + 0.2 < CurTime() and self:GetGrenade().Model then
local nade = self:GetGrenade()
local vm = self:GetVM()
local model = ClientsideModel(nade.Model or "models/weapons/tacint/v_quicknade_frag.mdl")
if !IsValid(model) then return end
model:SetParent(vm)
model:AddEffects(EF_BONEMERGE)
model:SetNoDraw(true)
if nade.Material then
model:SetMaterial(nade.Material)
end
self.QuickNadeModel = model
local tbl = {
Model = model,
Weapon = self
}
table.insert(TacRP.CSModelPile, tbl)
elseif !self:GetPrimedGrenade() and self.QuickNadeModel then
SafeRemoveEntity(self.QuickNadeModel)
self.QuickNadeModel = nil
end
end
if self:GetOwner():KeyPressed(IN_GRENADE1) then
self:PrimeGrenade()
elseif !tobool(self:GetOwner():GetInfo("tacrp_nademenu")) and self:GetOwner():KeyPressed(self.GrenadeMenuKey) then
self:SelectGrenade()
elseif tobool(self:GetOwner():GetInfo("tacrp_nademenu")) and self.GrenadeMenuKey != IN_GRENADE2 and !self:GetOwner():KeyDown(self.GrenadeMenuKey) then
self.GrenadeMenuKey = IN_GRENADE2
end
if CLIENT and self.GrenadeWaitSelect and self:GetOwner():HasWeapon(self.GrenadeWaitSelect) then
input.SelectWeapon(self:GetOwner():GetWeapon(self.GrenadeWaitSelect))
self.GrenadeWaitSelect = nil
end
if self:GetPrimedGrenade() and self:GetAnimLockTime() < CurTime() then
self:ThrowGrenade()
self:SetPrimedGrenade(false)
end
end

View File

@@ -0,0 +1,136 @@
function SWEP:GetRecoilResetTime(base)
if base then
return (self:GetBaseValue("RecoilResetInstant") and 0 or math.min(0.5, 60 / self:GetRPM(true))) + self:GetBaseValue("RecoilResetTime")
else
return (self:GetValue("RecoilResetInstant") and 0 or math.min(0.5, 60 / self:GetRPM())) + self:GetValue("RecoilResetTime")
end
end
function SWEP:ThinkRecoil()
if self:GetLastRecoilTime() + engine.TickInterval() + self:GetRecoilResetTime() < CurTime() then
local rec = self:GetRecoilAmount()
rec = rec - (FrameTime() * self:GetValue("RecoilDissipationRate"))
rec = math.Clamp(rec, 0, self:GetValue("RecoilMaximum"))
self:SetRecoilAmount(rec)
end
end
function SWEP:ApplyRecoil()
local rec = self:GetRecoilAmount()
local rps = self:GetValue("RecoilPerShot")
local cfm = self:GetCurrentFiremode()
if rec == 0 then
rps = rps * self:GetValue("RecoilFirstShotMult")
end
if self:GetOwner():Crouching() and self:GetOwner():OnGround() then
rps = rps * self:GetValue("RecoilMultCrouch")
end
if cfm < 0 then
rps = rps * self:GetValue("RecoilMultBurst")
elseif cfm == 1 then
rps = rps * self:GetValue("RecoilMultSemi")
end
if self:GetInBipod() then
rps = rps * math.min(1, self:GetValue("BipodRecoil"))
end
rec = rec + rps
rec = math.Clamp(rec, 0, self:GetValue("RecoilMaximum"))
if self:UseRecoilPatterns() then
self:SetRecoilDirection(self:GetRecoilPatternDirection(self:GetPatternCount()))
else
local stab = math.Clamp(self:GetValue("RecoilStability"), 0, 0.9)
self:SetRecoilDirection(util.SharedRandom("tacrp_recoildir", -180 + stab * 90, -stab * 90))
end
-- self:SetRecoilDirection(-90)
self:SetRecoilAmount(rec)
self:SetLastRecoilTime(CurTime())
local vis_kick = self:GetValue("RecoilVisualKick")
local vis_shake = 0
vis_kick = vis_kick * TacRP.ConVars["mult_recoil_vis"]:GetFloat()
vis_shake = 0
if self:GetInBipod() then
vis_kick = vis_kick * math.min(1, self:GetValue("BipodKick"))
vis_shake = math.max(0, 1 - self:GetValue("BipodKick"))
end
local vis_kick_v = vis_kick * 1
local vis_kick_h = vis_kick * util.SharedRandom("tacrp_vis_kick_h", -1, 1)
self:GetOwner():SetViewPunchAngles(Angle(vis_kick_v, vis_kick_h, vis_shake))
-- self:GetOwner():SetFOV(self:GetOwner():GetFOV() * 0.99, 0)
-- self:GetOwner():SetFOV(self:GetOwner():GetFOV(), 60 / (self:GetValue("RPM")))
end
function SWEP:RecoilDuration()
-- return self:GetValue("RecoilResetTime")
return 0.04 + math.Clamp(math.abs(self:GetValue("RecoilKick")) ^ 0.5, 0, 4) * 0.04
end
function SWEP:UseRecoilPatterns()
if !TacRP.ConVars["recoilpattern"]:GetBool() then return false end
if self:GetValue("ShootEnt") or self:GetValue("NoRecoilPattern") then return false end
if self:GetValue("RPM") <= 100 then return false end
if self:GetCurrentFiremode() < 0 then return false end
return true
end
SWEP.RecoilPatternCache = {}
SWEP.RecoilPatternSeedCache = nil
function SWEP:GetRecoilPatternDirection(shot)
local dir = 0
if !self.RecoilPatternSeedCache then
local cacheseed = self.RecoilPatternSeed or self:GetClass()
if isstring(cacheseed) then
local numseed = 0
for _, i in ipairs(string.ToTable(cacheseed)) do
numseed = numseed + string.byte(i)
end
numseed = numseed % 16777216
cacheseed = numseed
end
self.RecoilPatternSeedCache = cacheseed
end
local seed = self.RecoilPatternSeedCache + shot
if self.RecoilPatternCache[shot] then
dir = self.RecoilPatternCache[shot]
else
self.RecoilPatternCache[1] = 0
if self.RecoilPatternCache[shot - 1] then
--dir = self.RecoilPatternCache[shot - 1]
math.randomseed(seed)
local stab = math.Clamp(self:GetValue("RecoilStability"), 0, 0.9)
local max = self:GetBaseValue("RPM") / 60 * (1.1 + stab * 1.1)
local cap = 120 --math.Clamp(30 + shot * (90 / max), 30, 120)
--dir = dir + math.Rand(-stab * 90, stab * 90)
dir = Lerp(0.4 + (shot / max) * 0.6, self.RecoilPatternCache[shot - 1], math.Rand(-(1 - stab) * cap, (1 - stab) * cap))
if self:GetCurrentFiremode() != 1 then
dir = Lerp(shot / max, dir, math.Clamp(dir * 1.667, -cap, cap))
end
math.randomseed(CurTime() + self:EntIndex())
self.RecoilPatternCache[shot] = dir
-- print(shot, cap, max, dir)
else
dir = 0
end
end
return math.NormalizeAngle(dir - 90)
end

View File

@@ -0,0 +1,293 @@
function SWEP:Reload(force)
force = force or false
if self:GetOwner():IsNPC() then
self:NPC_Reload()
return
end
if self:GetValue("Firemodes") and self:GetOwner():KeyDown(IN_USE) and self:GetOwner():KeyPressed(IN_RELOAD) and self:GetFiremodeAmount() > 1 and !self:GetSafe() then
self:SwitchFiremode()
self:EmitSound("tacrp/weapons/pdw/fire_select-1.wav", 75, 100, 1, CHAN_ITEM)
return
end
local stop = self:RunHook("Hook_PreReload")
if stop then return end
if !self:GetOwner():KeyPressed(IN_RELOAD) and !force then
return
end
if self:StillWaiting(true) then return end
if self:GetJammed() then
local t = self:PlayAnimation("jam", 0.75, true, true)
self:GetOwner():DoCustomAnimEvent(PLAYERANIMEVENT_CANCEL_RELOAD, t * 1000)
self:SetJammed(false)
self:SetCharge(false)
return
end
if !self:CanReloadInSprint() and self:GetIsSprinting() then return end
if self:GetCapacity() <= 0 then return end
if self:Clip1() >= self:GetCapacity() then return end
if self:Ammo1() <= 0 and !self:GetInfiniteAmmo() then return end
self:ToggleBlindFire(TacRP.BLINDFIRE_NONE)
local mult = self:GetValue("ReloadTimeMult") / TacRP.ConVars["mult_reloadspeed"]:GetFloat()
local anim = "reload"
if self:GetValue("ShotgunReload") then
anim = "reload_start"
else
self:SetTimer(self:GetValue("LoadInTime") * mult, function()
self:SetLoadedRounds(math.min(self:GetCapacity(), self:Clip1() + self:Ammo1()))
self:DoBulletBodygroups()
end, "SetLoadedRounds")
if self.ReloadUpInTime then
self:SetTimer(self.ReloadUpInTime * mult, function()
self:RestoreClip(self:GetCapacity())
self:SetNthShot(0)
self:SetEndReload(true)
end, "ReloadUpIn")
end
end
local t = self:PlayAnimation(anim, mult, true, true)
self:GetOwner():DoCustomAnimEvent(PLAYERANIMEVENT_RELOAD, t * 1000)
if SERVER then
self:SetTimer(self.DropMagazineTime * mult, function()
self:DropMagazine()
end, "DropMagazine")
end
self:SetLoadedRounds(self:Clip1())
self:SetReloading(true)
self:SetEndReload(false)
self:SetEmptyReload(self:GetValue("ShotgunNoReverseStart") or self:Clip1() == 0)
self:DoBulletBodygroups()
self:RunHook("Hook_StartReload")
self:SetReloadFinishTime(CurTime() + (t * 0.95))
end
function SWEP:DropMagazine()
-- if !IsFirstTimePredicted() and !game.SinglePlayer() then return end
if self:GetValue("DropMagazineModel") and TacRP.ConVars["dropmagazinemodel"]:GetBool() then
local dropamt = math.floor(self:Clip1() / self:GetValue("DropMagazineAmount"))
local clip1 = self:Clip1()
for i = 1, self:GetValue("DropMagazineAmount") do
local mag = ents.Create("TacRP_droppedmag")
if IsValid(mag) then
local bone = "ValveBiped.Bip01_R_Hand"
if i == 2 then bone = "ValveBiped.Bip01_L_Hand" end
local matrix = self:GetOwner():GetBoneMatrix(self:GetOwner():LookupBone(bone) or -1)
local pos, ang
if matrix then
pos = matrix:GetTranslation()
ang = matrix:GetAngles()
else
pos = self:GetOwner():EyePos() - (self:GetOwner():EyeAngles():Up() * 8)
ang = self:GetOwner():EyeAngles()
end
mag:SetPos(pos)
mag:SetAngles(ang)
mag.Model = self:GetValue("DropMagazineModel")
mag.ImpactType = self:GetValue("DropMagazineImpact")
mag:SetOwner(self:GetOwner())
if clip1 > 0 and TacRP.ConVars["reload_dump"]:GetBool() then
local amt = (i == self:GetValue("DropMagazineAmount") and clip1) or dropamt
clip1 = clip1 - amt
if !self:GetInfiniteAmmo() then
mag.AmmoType = self:GetAmmoType()
mag.AmmoCount = amt
end
end
mag:Spawn()
local phys = mag:GetPhysicsObject()
if IsValid(phys) then
phys:AddAngleVelocity(Vector(math.Rand(-300, 300), math.Rand(-300, 300), math.Rand(-300, 300)))
end
end
end
self:SetClip1(clip1)
end
end
function SWEP:RestoreClip(amt)
local reserve = self:GetInfiniteAmmo() and math.huge or (self:Clip1() + self:Ammo1())
local lastclip1 = self:Clip1()
self:SetClip1(math.min(math.min(self:Clip1() + amt, self:GetCapacity()), reserve))
if !self:GetInfiniteAmmo() then
reserve = reserve - self:Clip1()
self:GetOwner():SetAmmo(reserve, self.Primary.Ammo)
end
return self:Clip1() - lastclip1
end
function SWEP:Unload(ammotype)
self:GetOwner():GiveAmmo(self:Clip1(), ammotype or self.Primary.Ammo)
self:SetClip1(0)
end
function SWEP:EndReload()
if self:GetValue("ShotgunReload") then
local mult = self:GetValue("ReloadTimeMult") / TacRP.ConVars["mult_reloadspeed"]:GetFloat()
if self:Clip1() >= self:GetCapacity() or (!self:GetInfiniteAmmo() and self:Ammo1() == 0) or self:GetEndReload() then
local cancellable = TacRP.ConVars["reload_sg_cancel"]:GetBool() and !self:GetValue("ShotgunFullCancel")
local t = 1
if !self.ShotgunNoReverseStart and (self:Clip1() == self:GetLoadedRounds() or !self:GetEmptyReload()) then
t = self:PlayAnimation("reload_start", -0.75 * mult, !cancellable, true)
else
t = self:PlayAnimation("reload_finish", mult, !cancellable, true)
end
self:GetOwner():DoCustomAnimEvent(PLAYERANIMEVENT_RELOAD_END, t * 1000)
self:SetReloading(false)
self:SetNthShot(0)
self:DoBulletBodygroups()
self:RunHook("Hook_EndReload")
else
local t = self:PlayAnimation("reload", mult, true)
local res = self:GetValue("ShotgunThreeload") and
math.min(math.min(3, self:GetCapacity() - self:Clip1()), self:GetInfiniteAmmo() and math.huge or self:Ammo1())
or 1
local delay = self:GetValue("ShotgunUpInTime")
for i = 1, res do
self:SetTimer(t * delay * ((i - 1) / 3) + 0.22, function()
self:GetOwner():DoCustomAnimEvent(PLAYERANIMEVENT_RELOAD_LOOP, t * 1000)
self:RestoreClip(1)
self:RunHook("Hook_InsertReload", res)
end, "ShotgunRestoreClip")
end
self:SetTimer(t * self:GetValue("ShotgunLoadInTime") * (res / 3), function()
self:SetLoadedRounds(self:GetLoadedRounds() + res)
self:DoBulletBodygroups()
end, "SetLoadedRounds")
self:SetReloadFinishTime(CurTime() + (t * delay * (res / 3)) + 0.05)
self:DoBulletBodygroups()
end
else
if !self.ReloadUpInTime then
self:RestoreClip(self:GetCapacity())
self:SetNthShot(0)
end
self:SetReloading(false)
self:SetEndReload(false)
self:RunHook("Hook_EndReload")
end
end
function SWEP:CancelReload(doanims, keeptime)
if self:GetReloading() then
self:RunHook("Hook_CancelReload")
local stop = false
if doanims then
if self:GetValue("ShotgunReload") then
local mult = self:GetValue("ReloadTimeMult") / TacRP.ConVars["mult_reloadspeed"]:GetFloat()
local t = 1
if self.CurrentAnimation == "reload_start" and self.ShotgunReloadCompleteStart then
self:SetEndReload(true)
elseif self:Clip1() == self:GetLoadedRounds() and !self.ShotgunNoReverseStart then
t = self:PlayAnimation("reload_start", -0.75 * mult, true, true)
stop = true
else
t = self:PlayAnimation("reload_finish", mult, true, true)
stop = true
end
self:GetOwner():DoCustomAnimEvent(PLAYERANIMEVENT_RELOAD_END, t * 1000)
else
self:Idle()
stop = true
end
else
stop = true
end
if stop then
self:KillTimer("SetLoadedRounds")
self:KillTimer("ShotgunRestoreClip")
self:KillTimer("ReloadUpIn")
self:KillTimer("DropMagazine")
self:SetReloading(false)
self:SetEndReload(false)
self:SetNthShot(0)
self:DoBulletBodygroups()
if !keeptime then
self:SetReloadFinishTime(0)
end
end
end
end
function SWEP:ThinkReload()
if self:GetReloading() and self:GetReloadFinishTime() < CurTime() then
self:EndReload()
end
end
local launcher_ammo = {
["smg1_grenade"] = true,
["rpg_round"] = true,
}
function SWEP:GetInfiniteAmmo()
local ammo = string.lower(self:GetAmmoType())
if launcher_ammo[ammo] then
return TacRP.ConVars["infinitelaunchers"]:GetBool() or self:GetValue("InfiniteAmmo")
else
return TacRP.ConVars["infiniteammo"]:GetBool() or self:GetValue("InfiniteAmmo")
end
end
function SWEP:GetCapacity(base)
if base then
return self:GetBaseValue("ClipSize")
else
return self:GetValue("ClipSize")
end
end
function SWEP:GetAmmoType(base)
local valfunc = base and self.GetBaseValue or self.GetValue
if self.Ammo_Expanded and TacRP.ConVars["expandedammotypes"]:GetBool() then
return valfunc(self, "Ammo_Expanded") or valfunc(self, "Ammo")
else
return valfunc(self, "Ammo")
end
end
-- Override to disable auto-reload for one reason or another.
function SWEP:ShouldAutoReload()
return true
end

View File

@@ -0,0 +1,398 @@
local blur = Material("pp/blurscreen")
local function drawBlurAt(x, y, w, h, amount, passes, reverse)
-- Intensity of the blur.
amount = amount or 5
surface.SetMaterial(blur)
surface.SetDrawColor(color_white)
local scrW, scrH = ScrW(), ScrH()
local x2, y2 = x / scrW, y / scrH
local w2, h2 = (x + w) / scrW, (y + h) / scrH
for i = -(passes or 0.2), 1, 0.2 do
if reverse then
blur:SetFloat("$blur", i * -1 * amount)
else
blur:SetFloat("$blur", i * amount)
end
blur:Recompute()
render.UpdateScreenEffectTexture()
surface.DrawTexturedRectUV(x, y, w, h, x2, y2, w2, h2)
end
end
local peekzoom = 1.2
function SWEP:ScopeToggle(setlevel)
if (setlevel or 0) > 0 and (!self:GetValue("Scope") or self:GetPrimedGrenade()) then return end
-- if setlevel and setlevel > 0 and self:GetAnimLockTime() > CurTime() or (!setlevel and self:GetAnimLockTime() > CurTime()) then return end
-- if (setlevel and setlevel > 0 and self:GetReloading()) or (!setlevel and self:GetReloading()) then return end
local level = self:GetScopeLevel()
local oldlevel = level
level = setlevel or (level + 1)
if level > self:GetValue("ScopeLevels") then
level = self:GetValue("ScopeLevels")
end
if self:GetCustomize() or self:GetLastMeleeTime() + 1 > CurTime() then -- self:SprintLock(true)
level = 0
end
if self:GetIsSprinting() and level > 0 then
if self:GetOwner():GetInfoNum("tacrp_aim_cancels_sprint", 0) > 0 and self:CanStopSprinting() then
self:GetOwner().TacRP_SprintBlock = true
else
level = 0
end
end
if self:DoOldSchoolScopeBehavior() then
level = 0
end
if level == self:GetScopeLevel() then return end
self:SetScopeLevel(level)
if level > 0 then
self:ToggleBlindFire(TacRP.BLINDFIRE_NONE)
end
if oldlevel == 0 or level == 0 then
self:SetLastScopeTime(CurTime())
end
if self:GetValue("AlwaysPeek") then
self:SetPeeking(true)
end
-- HACK: In singleplayer, SWEP:Think is called on client but IsFirstTimePredicted is NEVER true.
-- This causes ScopeToggle to NOT be called on client in singleplayer...
-- GenerateAutoSight needs to run clientside or scopes will break. Good old CallOnClient it is.
if SERVER and game.SinglePlayer() then
self:CallOnClient("GenerateAutoSight")
elseif CLIENT and (IsFirstTimePredicted() or game.SinglePlayer()) then
self:GenerateAutoSight()
self.LastHintLife = CurTime()
end
self:EmitSound(self:GetValue("Sound_ScopeIn"), 75, 100, 1, CHAN_ITEM)
self:SetShouldHoldType()
self:RunHook("Hook_PostScopeToggle", setlevel)
end
function SWEP:GetShouldFOV(ignorepeek)
local base = 90
if !ignorepeek and self:GetPeeking() then
return base / peekzoom
else
return base / self:GetMagnification()
end
end
function SWEP:IsInScope()
local sightdelta = self:Curve(self:GetSightDelta())
return (SERVER or !self:GetPeeking()) and !self:GetSafe() and ((self:GetScopeLevel() > 0 and sightdelta > 0.5) or (sightdelta > 0.9))
end
function SWEP:DoScope()
local h = ScrH()
local w = ScrW()
if self:IsInScope() then
local img = self:GetValue("ScopeOverlay")
if img then
-- assume players have a screen that is wider than it is tall because... that's stupid
local pos = self:GetOwner():EyePos()
pos = pos + self:GetShootDir():Forward() * 9000
local toscreen = pos:ToScreen()
local x = toscreen.x
local y = toscreen.y
local ss = math.Round(h * (self:GetValue("ScopeOverlaySize") or 1))
local sx = x - (ss / 2)
local sy = y - (ss / 2)
-- local shakey = math.min(cross * 35, 3)
-- sx = sx + math.Round(math.Rand(-shakey, shakey))
-- sy = sy + math.Round(math.Rand(-shakey, shakey))
-- local int = self:CheckFlashlightPointing()
-- if int > 0 then
-- surface.SetDrawColor(255, 255, 255, int * 250)
-- surface.DrawRect(0, 0, w, h)
-- end
surface.SetMaterial(img)
surface.SetDrawColor(255, 255, 255, 255)
surface.DrawTexturedRect(sx, sy, ss, ss)
surface.SetDrawColor(0, 0, 0)
surface.DrawRect(0, 0, w, sy)
surface.DrawRect(0, sy + ss, w, h - sy)
surface.DrawRect(0, 0, sx, h)
surface.DrawRect(sx + ss, 0, w - sx, h)
if self:GetReloading() then
drawBlurAt(0, 0, w, h, 1, 1)
end
-- if int > 0 then
-- surface.SetDrawColor(255, 255, 255, int * 25)
-- surface.DrawRect(0, 0, w, h)
-- end
if self:GetValue("ScopeDraw") then
self:GetValue("ScopeDraw")(self)
end
end
end
local blur_hook = self:RunHook("Hook_BlurScope")
if blur_hook then
if !istable(blur_hook) then blur_hook = {1, 1} end
drawBlurAt(0, 0, w, h, blur_hook[0], blur_hook[1])
end
end
function SWEP:GetSightDelta()
return self:GetSightAmount()
end
function SWEP:SetSightDelta(d)
self:SetSightAmount(d)
end
function SWEP:CanSight()
if self:GetReloading() and !TacRP.ConVars["ads_reload"]:GetBool() then return false end
return true
end
function SWEP:ThinkSights()
if !IsValid(self:GetOwner()) then return end
local ftp = IsFirstTimePredicted()
local ftsp = IsFirstTimePredicted() or !game.SinglePlayer()
if self:GetOwner():KeyDown(IN_USE) and self:GetOwner():KeyPressed(IN_ATTACK2) and ftsp then
self:ToggleSafety()
return
end
if ftp and self:GetValue("Bipod") and self:GetOwner():KeyPressed(IN_ATTACK2)
and !self:GetInBipod() and self:CanBipod() and ftsp then
self:EnterBipod()
end
local FT = FrameTime()
local sighted = self:GetScopeLevel() > 0
local amt = self:GetSightAmount()
local adst = self:GetAimDownSightsTime()
if ftp or game.SinglePlayer() then
if sighted then
if self:GetSprintLockTime() > CurTime() then
adst = adst + self:GetSprintToFireTime()
end
amt = math.Approach(amt, 1, FT / adst)
else
amt = math.Approach(amt, 0, FT / adst)
end
end
self:SetSightDelta(amt)
if self:GetSafe() then return end
if CLIENT then
self:ThinkPeek()
end
local toggle = self:GetOwner():GetInfoNum("tacrp_toggleaim", 0) == 1
local press, down = self:GetOwner():KeyPressed(IN_ATTACK2), self:GetOwner():KeyDown(IN_ATTACK2)
if (!self:GetValue("Scope") or self:DoOldSchoolScopeBehavior()) and !self.NoSecondaryMelee and down then
self:Melee()
elseif sighted and ((toggle and press and ftp) or (!toggle and !down)) then
self:ScopeToggle(0)
elseif !sighted and ((toggle and press and ftp) or (!toggle and down)) and self:CanSight() then
self:ScopeToggle(1)
elseif sighted and !self:CanSight() then
self:ScopeToggle(0)
end
end
function SWEP:GetMagnification()
local mag = 1
local level = self:GetScopeLevel()
if level > 0 then
if self:GetPeeking() then
return peekzoom
end
mag = 90 / self:GetValue("ScopeFOV")
mag = Lerp(level / self:GetValue("ScopeLevels"), 1, mag)
mag = self:RunHook("Hook_ModifyMagnification") or mag
end
if (mag <= 0) then
return 0.001 -- just in case
end
return mag
end
function SWEP:AdjustMouseSensitivity()
local mag = self:GetMagnification()
local sensmult = GetConVar("tacrp_aimsens"):GetFloat()
-- local aa = GetConVar("tacrp_aimassist")
-- local aac = GetConVar("tacrp_aimassist_cl")
-- local aai = GetConVar("tacrp_aimassist_intensity")
-- local aams = GetConVar("tacrp_aimassist_multsens")
-- if self:GetOwner().tacrp_AATarget != nil and aa:GetBool() and aac:GetBool()) then
-- aamult = aams:GetFloat() / aai:GetFloat()
-- else
-- aamult = 1
-- end
if mag > 1 then
return 1 / mag * math.Clamp(sensmult, 0.1, 1)
end
end
function SWEP:ThinkPeek()
end
function SWEP:GetCCIP(pos, ang)
-- get calculated point of impact
local sp, sa = self:GetMuzzleOrigin(), self:GetShootDir()
pos = pos or sp
ang = ang or sa
local v = self:GetValue("MuzzleVelocity")
local g = Vector(0, 0, -600)
local d = 1
local h = 0
if self:GetValue("ShootEnt") then
v = self:GetValue("ShootEntForce")
d = 0
g = physenv.GetGravity()
h = 4
end
local vel = ang:Forward() * v
local maxiter = 100
local timestep = 1 / 15
local gravity = timestep * g
local steps = {}
for i = 1, maxiter do
local dir = vel:GetNormalized()
local spd = vel:Length() * timestep
local drag = d * spd * spd * (1 / 150000)
if spd <= 0.001 then return nil end
local newpos = pos + (vel * timestep)
local newvel = vel - (dir * drag) + gravity
local tr
if h > 0 then
tr = util.TraceHull({
start = pos,
endpos = newpos,
filter = self:GetOwner(),
mask = MASK_SHOT,
mins = Vector(-h, -h, -h),
maxs = Vector(h, h, h),
})
else
tr = util.TraceLine({
start = pos,
endpos = newpos,
filter = self:GetOwner(),
mask = MASK_SHOT
})
end
table.insert(steps, 0, tr.HitPos)
if tr.Hit then
debugoverlay.Sphere(tr.HitPos, 8, 0.25, color_white, true)
return tr, i * timestep, steps
else
pos = newpos
vel = newvel
end
end
return nil
end
function SWEP:GetCorVal()
local vmfov = self.ViewModelFOV
local fov = self:GetShouldFOV()
return vmfov / (fov * 1.33333)
end
function SWEP:HasOptic()
return self:GetValue("Scope") and (self:GetValue("ScopeOverlay") or self:GetValue("Holosight"))
end
function SWEP:DoOldSchoolScopeBehavior()
return (TacRP.ConVars["oldschool"]:GetBool() or TacRP.GetBalanceMode() == TacRP.BALANCE_OLDSCHOOL)
and !self:HasOptic()
end
function SWEP:GetAimDownSightsTime(base)
if base then
return self:GetBaseValue("AimDownSightsTime") * TacRP.ConVars["mult_aimdownsights"]:GetFloat()
else
return self:GetValue("AimDownSightsTime") * TacRP.ConVars["mult_aimdownsights"]:GetFloat()
end
end
function SWEP:GetSprintToFireTime(base)
if base then
return self:GetBaseValue("SprintToFireTime") * TacRP.ConVars["mult_sprinttofire"]:GetFloat()
else
return self:GetValue("SprintToFireTime") * TacRP.ConVars["mult_sprinttofire"]:GetFloat()
end
end
function SWEP:GetPeeking()
return (!self.InversePeek and self:GetNWPeeking()) or (self.InversePeek and !self:GetNWPeeking())
end
function SWEP:SetPeeking(b)
if self.InversePeek then
self:SetNWPeeking(!b)
else
self:SetNWPeeking(b)
end
end

View File

@@ -0,0 +1,872 @@
function SWEP:StillWaiting(cust, reload)
if self:GetNextPrimaryFire() > CurTime() then return true end
if self:GetNextSecondaryFire() > CurTime() and (!reload or !(reload and self:GetReloading())) then return true end
if self:GetAnimLockTime() > CurTime() and (!reload or !(reload and self:GetReloading())) then return true end
if !cust and self:GetBlindFireFinishTime() > CurTime() then return true end
if !cust and self:GetCustomize() then return true end
if self:GetPrimedGrenade() then return true end
return false
end
function SWEP:SprintLock(shoot)
if self:GetSprintLockTime() > CurTime() or self:GetIsSprinting() or self:ShouldLowerWeapon() then
return true
end
if shoot and self:DoForceSightsBehavior() and (self:GetSprintDelta() > 0 or self:GetSightDelta() < 0.75) and !self:GetBlindFire() then
return true
end
if self:GetValue("CannotHipFire") and self:GetSightAmount() < 1 and !self:GetBlindFire() then
return true
end
return false
end
local function anglerotate(main, off)
local forward, up, right = main:Forward(), main:Up(), main:Right()
main:RotateAroundAxis(right, off.p)
main:RotateAroundAxis(up, off.y)
main:RotateAroundAxis(forward, off.r)
return main
end
function SWEP:PrimaryAttack()
if self:GetOwner():IsNPC() then
self:NPC_PrimaryAttack()
return
end
if self:GetValue("Melee") and self:GetOwner():KeyDown(IN_USE) and !(self:GetValue("RunawayBurst") and self:GetBurstCount() > 0) then
-- self.Primary.Automatic = false
self:SetSafe(false)
self:Melee()
return
end
-- if self:GetJammed() then return end
if self:GetCurrentFiremode() < 0 and self:GetBurstCount() >= -self:GetCurrentFiremode() then return end
if self:GetReloading() and self:GetValue("ShotgunReload") then
if TacRP.ConVars["reload_sg_cancel"]:GetBool() and !self:GetValue("ShotgunFullCancel") then
self:CancelReload(false)
self:Idle()
else
self:CancelReload(true)
end
end
if self:SprintLock(true) then return end
if DarkRP and self:GetNWBool("TacRP_PoliceBiocode") and !self:GetOwner():isCP() then return end
if self:GetSafe() and !self:GetReloading() then self:ToggleSafety(false) return end
if self:StillWaiting() then return end
if self:GetValue("RequireLockOn") and !(IsValid(self:GetLockOnEntity()) and CurTime() > self:GetLockOnStartTime() + self:GetValue("LockOnTime")) then return end
if self:Clip1() < self:GetValue("AmmoPerShot") or self:GetJammed() then
local ret = self:RunHook("Hook_PreDryfire")
if ret != true then
self.Primary.Automatic = false
if self:GetBlindFire() then
self:PlayAnimation("blind_dryfire")
else
self:PlayAnimation("dryfire")
end
self:EmitSound(self:GetValue("Sound_DryFire"), 75, 100, 1, CHAN_ITEM)
self:SetBurstCount(0)
self:SetNextPrimaryFire(CurTime() + 0.2)
self:RunHook("Hook_PostDryfire")
return
end
end
if util.SharedRandom("tacRP_shootChance", 0, 1) <= self:GetJamChance(false) then
local ret = self:RunHook("Hook_PreJam")
if ret != true then
if self:GetBurstCount() == 0 then
self.Primary.Automatic = false
end
if self:GetBlindFire() then
self:PlayAnimation("blind_dryfire")
else
self:PlayAnimation("dryfire")
end
self:EmitSound(self:GetValue("Sound_Jam"), 75, 100, 1, CHAN_ITEM)
self:SetBurstCount(0)
self:SetPatternCount(0)
self:SetNextPrimaryFire(CurTime() + self:GetValue("JamWaitTime"))
self:SetNextSecondaryFire(CurTime() + self:GetValue("JamWaitTime"))
if self:GetValue("JamTakesRound") then
self:TakePrimaryAmmo(self:GetValue("AmmoPerShot"))
end
if self:Clip1() > 0 and !self:GetValue("JamSkipFix") then
self:SetJammed(true)
end
self:RunHook("Hook_PostJam")
return
end
end
self:SetBaseSettings()
local stop = self:RunHook("Hook_PreShoot")
if stop then return end
local seq = "fire"
local idle = true
local mult = self:GetValue("ShootTimeMult")
if self:GetValue("LastShot") and self:Clip1() == self:GetValue("AmmoPerShot") then
seq = self:TranslateSequence("lastshot")
idle = false
end
if self:GetBlindFire() then
seq = "blind_" .. seq
end
if self:GetValue("Akimbo") and !self:GetBlindFire() then
if self:GetNthShot() % 2 == 0 then
seq = "shoot_left"
else
seq = "shoot_right"
end
if self:GetValue("LastShot") then
if self:Clip1() == self:GetValue("AmmoPerShot") then
seq = seq .. "_lastshot"
elseif self:Clip1() == self:GetValue("AmmoPerShot") * 2 then
seq = seq .. "_second_2_lastshot"
end
end
end
local prociron = self:DoProceduralIrons()
if self:GetScopeLevel() > 0 and (prociron or self:HasSequence(seq .. "_iron")) and !self:GetPeeking() then
if prociron then
if self:GetValue("LastShot") and self:Clip1() == self:GetValue("AmmoPerShot") then
self:PlayAnimation(self:TranslateSequence("dryfire"), mult, false)
end
self:SetLastProceduralFireTime(CurTime())
else
self:PlayAnimation(seq .. "_iron", mult, false, idle)
end
elseif self:HasSequence(seq .. "1") then
local seq1 = seq .. "1"
if !self:GetInBipod() and (self:GetScopeLevel() < 1 or self:GetPeeking()) then
seq1 = seq .. tostring(self:GetBurstCount() + 1)
end
if self:HasSequence(seq1) then
self:PlayAnimation(seq1, mult, false, idle)
elseif self:GetScopeLevel() < 1 or self:GetPeeking() then
for i = self:GetBurstCount() + 1, 1, -1 do
local seq2 = seq .. tostring(i)
if self:HasSequence(seq2) then
self:PlayAnimation(seq2, mult, false, idle)
break
end
end
end
else
self:PlayAnimation(seq, mult, false, idle)
end
self:GetOwner():DoCustomAnimEvent(PLAYERANIMEVENT_ATTACK_PRIMARY, 0)
local pvar = self:GetValue("ShootPitchVariance")
local sshoot = self:GetValue("Sound_Shoot")
if self:GetValue("Silencer") then
sshoot = self:GetValue("Sound_Shoot_Silenced")
end
if istable(sshoot) then
sshoot = table.Random(sshoot)
end
if self:GetValue("Sound_ShootAdd") then
self:EmitSound(self:GetValue("Sound_ShootAdd"), self:GetValue("Vol_Shoot"), self:GetValue("Pitch_Shoot") + util.SharedRandom("TacRP_sshoot", -pvar, pvar), self:GetValue("Loudness_Shoot"), CHAN_BODY)
end
-- if we die from suicide, EmitSound will not play, so do this instead
if self:GetBlindFireMode() == TacRP.BLINDFIRE_KYS then
if SERVER then
sound.Play(sshoot, self:GetMuzzleOrigin(), self:GetValue("Vol_Shoot"), self:GetValue("Pitch_Shoot") + util.SharedRandom("TacRP_sshoot", -pvar, pvar), self:GetValue("Loudness_Shoot"))
end
else
self:EmitSound(sshoot, self:GetValue("Vol_Shoot"), self:GetValue("Pitch_Shoot") + util.SharedRandom("TacRP_sshoot", -pvar, pvar), self:GetValue("Loudness_Shoot"), CHAN_WEAPON)
end
local delay = 60 / self:GetRPM()
-- local delay = 60 / self:GetRPM()
local curatt = self:GetNextPrimaryFire()
local diff = CurTime() - curatt
if diff > engine.TickInterval() or diff < 0 then
curatt = CurTime()
end
self:SetNthShot(self:GetNthShot() + 1)
local ejectdelay = self:GetValue("EjectDelay")
if ejectdelay == 0 then
self:DoEject()
else
self:SetTimer(ejectdelay, function()
self:DoEject()
end)
end
self:DoEffects()
if self:GetValue("EffectsDoubled") then
-- self:SetNthShot(self:GetNthShot() + 1)
self:DoEffects(true)
if ejectdelay == 0 then
self:DoEject(true)
else
self:SetTimer(ejectdelay, function()
self:DoEject(true)
end)
end
-- self:SetNthShot(self:GetNthShot() - 1)
end
local num = self:GetValue("Num")
local fixed_spread = self:IsShotgun() and TacRP.ConVars["fixedspread"]:GetBool()
local pellet_spread = self:IsShotgun() and self:GetValue("ShotgunPelletSpread") > 0 and TacRP.ConVars["pelletspread"]:GetBool()
local spread = self:GetSpread()
local dir = self:GetShootDir()
local tr = self:GetValue("TracerNum")
local shootent = self:GetValue("ShootEnt")
if IsFirstTimePredicted() then
local hitscan = !TacRP.ConVars["physbullet"]:GetBool()
local dist = 100000
-- If the bullet is going to hit something very close in front, use hitscan bullets instead
-- This uses the aim direction without random spread, which may result in hitscan bullets in distances where it shouldn't be.
if !hitscan and (game.SinglePlayer() or !TacRP.ConVars["client_damage"]:GetBool()) then
dist = math.max(self:GetValue("MuzzleVelocity"), 15000) * engine.TickInterval()
* game.GetTimeScale()
* (num == 1 and 2 or 1) * (game.IsDedicated() and 1 or 2)
local threshold = dir:Forward() * dist
local inst_tr = util.TraceLine({
start = self:GetMuzzleOrigin(),
endpos = self:GetMuzzleOrigin() + threshold,
mask = MASK_SHOT,
filter = {self:GetOwner(), self:GetOwner():GetVehicle(), self},
})
if inst_tr.Hit and !inst_tr.HitSky then
hitscan = true
end
-- debugoverlay.Line(self:GetMuzzleOrigin(), self:GetMuzzleOrigin() + threshold, 2, hitscan and Color(255, 0, 255) or Color(255, 255, 255))
end
-- Firebullets already does this so this is just placebo
-- self:GetOwner():LagCompensation(true)
if shootent or !hitscan or fixed_spread then
local d = math.random() -- self:GetNthShot() / self:GetCapacity()
for i = 1, num do
local new_dir = Angle(dir)
if fixed_spread then
local sgp_x, sgp_y = self:GetShotgunPattern(i, d)
// new_dir:Add(Angle(sgp_x, sgp_y, 0) * 36 * 1.4142135623730)
new_dir = anglerotate(new_dir, Angle(sgp_x, sgp_y, 0) * 36 * 1.4142135623730)
if pellet_spread then
// new_dir:Add(self:RandomSpread(self:GetValue("ShotgunPelletSpread"), i))
new_dir = anglerotate(new_dir, self:RandomSpread(self:GetValue("ShotgunPelletSpread"), i))
end
else
// new_dir:Add(self:RandomSpread(spread, i))
new_dir = anglerotate(new_dir, self:RandomSpread(spread, i))
end
if shootent then
self:ShootRocket(new_dir)
elseif hitscan then
self:GetOwner():FireBullets({
Damage = self:GetValue("Damage_Max"),
Force = 8,
Tracer = tr,
TracerName = "tacrp_tracer",
Num = 1,
Dir = new_dir:Forward(),
Src = self:GetMuzzleOrigin(),
Spread = Vector(),
IgnoreEntity = self:GetOwner():GetVehicle(),
Distance = dist,
HullSize = (self:IsShotgun() and i % 2 == 0) and TacRP.ShotgunHullSize or 0,
Callback = function(att, btr, dmg)
local range = (btr.HitPos - btr.StartPos):Length()
self:AfterShotFunction(btr, dmg, range, self:GetValue("Penetration"), {})
-- if SERVER then
-- debugoverlay.Cross(btr.HitPos, 4, 5, Color(255, 0, 0), false)
-- else
-- debugoverlay.Cross(btr.HitPos, 4, 5, Color(255, 255, 255), false)
-- end
end
})
else
TacRP:ShootPhysBullet(self, self:GetMuzzleOrigin(), new_dir:Forward() * self:GetValue("MuzzleVelocity"),
{HullSize = (self:IsShotgun() and i % 2 == 0) and TacRP.ShotgunHullSize or 0,})
end
end
else
local new_dir = Angle(dir)
local new_spread = spread
-- if pellet_spread then
-- new_spread = self:GetValue("ShotgunPelletSpread")
-- new_dir:Add(self:RandomSpread(spread, 0))
-- end
-- Try to use Num in FireBullets if at all possible, as this is more performant and better for damage calc compatibility
-- Also it generates nice big numbers in various hit number addons instead of a buncha small ones.
self:GetOwner():FireBullets({
Damage = self:GetValue("Damage_Max"),
Force = 8,
Tracer = tr,
TracerName = "tacrp_tracer",
Num = num,
Dir = new_dir:Forward(),
Src = self:GetMuzzleOrigin(),
Spread = Vector(new_spread, new_spread, 0),
IgnoreEntity = self:GetOwner():GetVehicle(),
Distance = dist,
Callback = function(att, btr, dmg)
local range = (btr.HitPos - btr.StartPos):Length()
if IsValid(btr.Entity) and (!game.SinglePlayer() and TacRP.ConVars["client_damage"]:GetBool()) then
if CLIENT then
net.Start("tacrp_clientdamage")
net.WriteEntity(self)
net.WriteEntity(btr.Entity)
net.WriteVector(btr.Normal)
net.WriteVector(btr.Entity:WorldToLocal(btr.HitPos))
net.WriteUInt(btr.HitGroup, 8)
net.WriteFloat(range)
net.WriteFloat(self:GetValue("Penetration"))
net.WriteUInt(0, 4)
net.SendToServer()
else
self:AfterShotFunction(btr, dmg, range, self:GetValue("Penetration"), {[btr.Entity] = true})
end
else
self:AfterShotFunction(btr, dmg, range, self:GetValue("Penetration"), {})
end
if SERVER then
debugoverlay.Cross(btr.HitPos, 4, 5, Color(255, 0, 0), false)
else
debugoverlay.Cross(btr.HitPos, 4, 5, Color(255, 255, 255), false)
end
end
})
end
-- self:GetOwner():LagCompensation(false)
end
self:ApplyRecoil()
self:SetNextPrimaryFire(curatt + delay)
self:TakePrimaryAmmo(self:GetValue("AmmoPerShot"))
self:SetBurstCount(self:GetBurstCount() + 1)
self:SetPatternCount(self:GetPatternCount() + 1)
self:DoBulletBodygroups()
if self:Clip1() == 0 then self.Primary.Automatic = false end
-- FireBullets won't hit ourselves. Apply damage directly!
if SERVER and self:GetBlindFireMode() == TacRP.BLINDFIRE_KYS and !self:GetValue("ShootEnt") then
timer.Simple(0, function()
if !IsValid(self) or !IsValid(self:GetOwner()) then return end
local damage = DamageInfo()
damage:SetAttacker(self:GetOwner())
damage:SetInflictor(self)
damage:SetDamage(self:GetValue("Damage_Max") * self:GetValue("Num") * self:GetConfigDamageMultiplier())
damage:SetDamageType(self:GetValue("DamageType") or self:IsShotgun() and DMG_BUCKSHOT or DMG_BULLET)
damage:SetDamagePosition(self:GetMuzzleOrigin())
damage:SetDamageForce(dir:Forward() * self:GetValue("Num"))
damage:ScaleDamage(self:GetBodyDamageMultipliers()[HITGROUP_HEAD])
-- self:GetOwner():SetLastHitGroup(HITGROUP_HEAD)
self:GetOwner():TakeDamageInfo(damage)
end)
end
if CLIENT and self:GetOwner() == LocalPlayer() then
self:DoMuzzleLight()
elseif game.SinglePlayer() then
self:CallOnClient("DoMuzzleLight")
end
self:SetCharge(false)
-- Troll
if self:GetBurstCount() >= 8 and TacRP.ShouldWeFunny(true) and (self.NextTroll or 0) < CurTime() and math.random() <= 0.02 then
timer.Simple(math.Rand(0, 0.25), function()
if IsValid(self) then
self:EmitSound("tacrp/discord-notification.wav", nil, 100, math.Rand(0.1, 0.5), CHAN_BODY)
end
end)
self.NextTroll = CurTime() + 180
end
self:RunHook("Hook_PostShoot")
end
local rings = {1, 9, 24, 45}
local function ringnum(i)
return rings[i] or (rings[#rings] + i ^ 2)
end
local function getring(x)
local i = 1
while x > ringnum(i) do i = i + 1 end
return i
end
function SWEP:GetShotgunPattern(i, d)
local ring_spread = self:GetSpread()
local num = self:GetValue("Num")
if num == 1 then return 0, 0 end
local pelspread = self:GetValue("ShotgunPelletSpread") > 0 and TacRP.ConVars["pelletspread"]:GetBool()
if pelspread then
ring_spread = ring_spread - self:GetValue("ShotgunPelletSpread")
else
d = 0
end
local x = 0
local y = 0
local red = num <= 3 and 0 or 1
local f = (i - red) / (num - red)
if num == 2 then
local angle = f * 180 + (pelspread and (d - 0.5) * 60 or 0)
x = math.sin(math.rad(angle)) * ring_spread
y = math.cos(math.rad(angle)) * ring_spread
elseif num == 3 then
local angle = f * 360 + d * 180 + 30
x = math.sin(math.rad(angle)) * ring_spread
y = math.cos(math.rad(angle)) * ring_spread
elseif i == 1 then
return x, y
-- elseif num <= 9 then
-- local angle = 360 * (f + d - (1 / (num - 2)))
-- x = math.sin(math.rad(angle)) * ring_spread
-- y = math.cos(math.rad(angle)) * ring_spread
else
local tr = getring(num)
local ri = getring(i)
local rin = ringnum(ri)
local rln = ringnum(ri - 1)
local l = (ri - 1) / (tr - 1)
if ri == tr then
f = (i - rln) / ((math.min(rin, num)) - rln)
else
f = (i - rln) / (rin - rln)
end
local angle = 360 * (f + l + d)
x = math.sin(math.rad(angle)) * ring_spread * l
y = math.cos(math.rad(angle)) * ring_spread * l
end
return x, y
end
local doorclasses = {
["func_door_rotating"] = true,
["prop_door_rotating"] = true,
["prop_door_rotating_checkpoint"] = true
}
function SWEP:AfterShotFunction(tr, dmg, range, penleft, alreadypenned, forced)
if !forced and !IsFirstTimePredicted() and !game.SinglePlayer() then return end
if self:GetValue("DamageType") then
dmg:SetDamageType(self:GetValue("DamageType"))
elseif self:IsShotgun() then
dmg:SetDamageType(DMG_BUCKSHOT + (engine.ActiveGamemode() == "terrortown" and DMG_BULLET or 0))
end
local matpen = self:GetValue("Penetration")
if tr.Entity and alreadypenned[tr.Entity] then
dmg:SetDamage(0)
elseif IsValid(tr.Entity) then
dmg:SetDamage(self:GetDamageAtRange(range))
local bodydamage = self:GetBodyDamageMultipliers()
if bodydamage[tr.HitGroup] then
dmg:ScaleDamage(bodydamage[tr.HitGroup])
end
if tr.Entity:IsNextBot() or tr.Entity:IsNPC() then
dmg:ScaleDamage(self:GetValue("DamageMultNPC"))
end
TacRP.CancelBodyDamage(tr.Entity, dmg, tr.HitGroup)
if self:GetOwner():IsNPC() and !TacRP.ConVars["npc_equality"]:GetBool() then
dmg:ScaleDamage(0.25)
elseif matpen > 0 and TacRP.ConVars["penetration"]:GetBool() and !self:GetOwner():IsNPC() then
local pendelta = penleft / matpen
pendelta = Lerp(pendelta, math.Clamp(matpen * 0.02, 0.25, 0.5), 1)
dmg:ScaleDamage(pendelta)
end
alreadypenned[tr.Entity] = true
if tr.Entity.LVS and !self:IsShotgun() then
dmg:ScaleDamage(0.5)
dmg:SetDamageForce(dmg:GetDamageForce():GetNormalized() * matpen * 75)
dmg:SetDamageType(DMG_AIRBOAT + DMG_SNIPER)
penleft = 0
end
if SERVER and self:GetValue("DamageType") == DMG_BURN and IsValid(tr.Entity) then
tr.Entity:Ignite(1, 64)
end
end
if self:GetValue("ExplosiveDamage") > 0 and penleft == matpen then
-- Add DMG_AIRBOAT to hit helicopters
-- Need a timer here because only one DamageInfo can exist at a time
timer.Simple(0.0001, function()
if !IsValid(self) or !IsValid(self:GetOwner()) then return end
local dmginfo = DamageInfo()
dmginfo:SetAttacker(self:GetOwner())
dmginfo:SetInflictor(self)
dmginfo:SetDamageType(self:GetValue("ExplosiveDamageType") or (DMG_BLAST + DMG_AIRBOAT))
dmginfo:SetDamage(self:GetValue("ExplosiveDamage"))
util.BlastDamageInfo(dmginfo, tr.HitPos, self:GetValue("ExplosiveRadius"))
end)
-- penleft = 0
--util.BlastDamage(self, self:GetOwner(), tr.HitPos, self:GetValue("ExplosiveRadius"), self:GetValue("ExplosiveDamage"))
end
if self:GetValue("ExplosiveEffect") then
local fx = EffectData()
fx:SetOrigin(tr.HitPos)
fx:SetNormal(tr.HitNormal)
if bit.band(util.PointContents(tr.HitPos), CONTENTS_WATER) == CONTENTS_WATER then
util.Effect("WaterSurfaceExplosion", fx, true)
else
util.Effect(self:GetValue("ExplosiveEffect"), fx, true)
end
end
if SERVER and IsValid(tr.Entity) and !tr.Entity.TacRP_DoorBusted
and doorclasses[tr.Entity:GetClass()] and self:GetValue("DoorBreach") then
if !tr.Entity.TacRP_BreachThreshold or CurTime() - tr.Entity.TacRP_BreachThreshold[1] > 0.1 then
tr.Entity.TacRP_BreachThreshold = {CurTime(), 0}
end
tr.Entity.TacRP_BreachThreshold[2] = tr.Entity.TacRP_BreachThreshold[2] + dmg:GetDamage()
if tr.Entity.TacRP_BreachThreshold[2] > (self:GetValue("DoorBreachThreshold") or 100) then
tr.Entity:EmitSound("ambient/materials/door_hit1.wav", 80, math.Rand(95, 105))
for _, otherDoor in pairs(ents.FindInSphere(tr.Entity:GetPos(), 72)) do
if tr.Entity != otherDoor and otherDoor:GetClass() == tr.Entity:GetClass() then
local v = (otherDoor.TacRP_BreachThreshold and CurTime() - otherDoor.TacRP_BreachThreshold[1] <= 0.1) and 800 or 200
TacRP.DoorBust(otherDoor, tr.Normal * v, dmg:GetAttacker())
break
end
end
TacRP.DoorBust(tr.Entity, tr.Normal * 800, dmg:GetAttacker())
tr.Entity.TacRP_BreachThreshold = nil
end
end
self:Penetrate(tr, range, penleft, alreadypenned)
end
function SWEP:GetMinMaxRange(base, static)
local valfunc = base and self.GetBaseValue or self.GetValue
local max, min = valfunc(self, "Damage_Max"), valfunc(self, "Damage_Min")
return valfunc(self, "Range_Min", static, max < min), valfunc(self, "Range_Max", static, max < min)
end
function SWEP:GetDamageAtRange(range, noround)
local d = 1
local r_min, r_max = self:GetMinMaxRange()
if range <= r_min then
d = 0
elseif range >= r_max then
d = 1
else
d = (range - r_min) / (r_max - r_min)
end
local dmgv = Lerp(d, self:GetValue("Damage_Max"), self:GetValue("Damage_Min")) * self:GetConfigDamageMultiplier()
if !noround then
dmgv = math.ceil(dmgv)
end
return dmgv
end
function SWEP:GetShootDir(nosway)
if !IsValid(self:GetOwner()) then return self:GetAngles() end
local dir = self:GetOwner():EyeAngles()
local bf = self:GetBlindFireMode()
if bf == TacRP.BLINDFIRE_KYS then
dir.y = dir.y + 180
elseif bf == TacRP.BLINDFIRE_LEFT then
dir.y = dir.y + 75
elseif bf == TacRP.BLINDFIRE_RIGHT then
dir.y = dir.y - 75
end
local u, r = dir:Up(), dir:Right()
local oa = self:GetFreeAimOffset()
if !nosway then
oa = oa + self:GetSwayAngles()
end
dir:RotateAroundAxis(u, oa.y)
-- dir:RotateAroundAxis(r, oa.r)
dir:RotateAroundAxis(r, -oa.p)
dir = dir + self:GetValue("ShootOffsetAngle")
return dir
end
function SWEP:ShootRocket(dir)
if CLIENT then return end
local src = self:GetMuzzleOrigin()
dir = dir or self:GetShootDir()
local ent = self:GetValue("ShootEnt")
local rocket = ents.Create(ent)
if !IsValid(rocket) then return end
rocket:SetPos(src)
if self:GetBlindFireMode() != TacRP.BLINDFIRE_KYS then
rocket:SetOwner(self:GetOwner())
else
rocket.Attacker = self:GetOwner()
end
rocket.Inflictor = self
rocket:SetAngles(dir)
if isfunction(rocket.SetWeapon) then
rocket:SetWeapon(self)
end
if self:GetOwner():IsNPC() then
rocket.LockOnEntity = self:GetOwner():GetTarget()
else
if IsValid(self:GetLockOnEntity()) and CurTime() >= self:GetValue("LockOnTime") + self:GetLockOnStartTime() then
rocket.LockOnEntity = self:GetLockOnEntity()
end
end
self:RunHook("Hook_PreShootEnt", rocket)
rocket:Spawn()
self:RunHook("Hook_PostShootEnt", rocket)
local phys = rocket:GetPhysicsObject()
if phys:IsValid() and self:GetValue("ShootEntForce") > 0 then
phys:SetVelocityInstantaneous(dir:Forward() * self:GetValue("ShootEntForce"))
end
end
function SWEP:GetSpread(baseline)
local ply = self:GetOwner()
local spread = self:GetValue("Spread")
if baseline then return spread end
local hippenalty = self:GetValue("HipFireSpreadPenalty")
local movepenalty = self:GetValue("MoveSpreadPenalty")
if TacRP.ConVars["oldschool"]:GetBool() or TacRP.GetBalanceMode() == TacRP.BALANCE_OLDSCHOOL then
movepenalty = movepenalty + hippenalty * 0.25
hippenalty = hippenalty * Lerp(12 / (self:GetValue("ScopeFOV") - 1.1), 0.05, 0.5)
end
if self:GetInBipod() and self:GetScopeLevel() == 0 then
spread = spread + Lerp(1 - self:GetValue("PeekPenaltyFraction"), hippenalty, 0)
else
spread = spread + Lerp(self:GetSightAmount() - (self:GetPeeking() and self:GetValue("PeekPenaltyFraction") or 0), hippenalty, 0)
end
if !self:UseAltRecoil() then
spread = spread + (self:GetRecoilAmount() * self:GetValue("RecoilSpreadPenalty"))
end
local v = ply:GetAbsVelocity()
local spd = math.min(math.sqrt(v.x * v.x + v.y * v.y) / 250, 1)
spread = spread + (spd * movepenalty)
local groundtime = CurTime() - (ply.TacRP_LastOnGroundTime or 0)
local gd = math.Clamp(!ply:IsOnGround() and 0 or groundtime / math.Clamp((ply.TacRP_LastAirDuration or 0) - 0.25, 0.1, 1.5), 0, 1) ^ 0.75
if gd < 1 and ply:GetMoveType() != MOVETYPE_NOCLIP then
local v = (ply:WaterLevel() > 0 or ply:GetMoveType() == MOVETYPE_LADDER) and 0.5 or 0
spread = spread + Lerp(gd + v, self:GetValue("MidAirSpreadPenalty"), 0)
end
if ply:OnGround() and ply:Crouching() then
spread = spread + self:GetValue("CrouchSpreadPenalty")
end
if self:GetBlindFire() then
spread = spread + self:GetValue("BlindFireSpreadPenalty")
end
local quickscopetime = CurTime() - self:GetLastScopeTime()
local qsd = (quickscopetime / self:GetValue("QuickScopeTime")) ^ 4
if qsd < 1 then
spread = spread + Lerp(qsd, self:GetValue("QuickScopeSpreadPenalty"), 0)
end
spread = math.max(spread, 0)
return spread
end
local type_to_cvar = {
["2Magnum Pistol"] = "mult_damage_magnum",
["7Sniper Rifle"] = "mult_damage_sniper",
-- ["5Shotgun"] = "mult_damage_shotgun",
["6Launcher"] = "",
["7Special Weapon"] = "",
["8Melee Weapon"] = "",
["9Equipment"] = "",
["9Throwable"] = "",
}
function SWEP:GetConfigDamageMultiplier()
if self:IsShotgun() then
return TacRP.ConVars["mult_damage_shotgun"]:GetFloat()
elseif self:GetValue("PrimaryMelee") then
return TacRP.ConVars["mult_damage_melee"]:GetFloat()
else
local cvar = type_to_cvar[self.SubCatType] or "mult_damage"
return TacRP.ConVars[cvar] and TacRP.ConVars[cvar]:GetFloat() or 1
end
end
local shotgundmgmult = {
[HITGROUP_HEAD] = 1,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 1,
[HITGROUP_RIGHTLEG] = 1,
[HITGROUP_GEAR] = 1,
}
function SWEP:GetBodyDamageMultipliers(base)
if self:IsShotgun(base) then -- Shotguns using hull traces will never hit bodygroups
return table.Copy(shotgundmgmult)
end
local valfunc = base and self.GetBaseValue or self.GetValue
local btbl = table.Copy(valfunc(self, "BodyDamageMultipliers"))
for k, v in pairs(valfunc(self, "BodyDamageMultipliersExtra") or {}) do
if v < 0 then
btbl[k] = math.abs(v)
else
btbl[k] = btbl[k] * v
end
end
local mult = TacRP.ConVars["mult_headshot"]:GetFloat()
if mult <= 0 then
btbl[HITGROUP_HEAD] = 1
elseif mult <= 1 then
btbl[HITGROUP_HEAD] = Lerp(mult, 1, btbl[HITGROUP_HEAD])
else
btbl[HITGROUP_HEAD] = btbl[HITGROUP_HEAD] * mult
end
return btbl
end
function SWEP:FireAnimationEvent( pos, ang, event, options )
if event != 5004 then return true end
end
-- DO NOT USE AngleRand() to do bullet spread as it generates a random angle in 3 directions when we only use two (roll is not relevant!)
-- Also, multiplying by 36 is not correct! you need to also multiply by square root of 2. Trig stuff, i forgot why exactly.
-- Arctic I fixed this THREE FUCKING TIMES on your THREE FUCKING WEAPON BASES do not make me come to Australia and beat the shit out of you
function SWEP:RandomSpread(spread, seed)
seed = (seed or 0) + self:EntIndex() + engine.TickCount()
local a = util.SharedRandom("tacrp_randomspread", 0, 360, seed)
local angleRand = Angle(math.sin(a), math.cos(a), 0)
angleRand:Mul(spread * util.SharedRandom("tacrp_randomspread2", 0, 45, seed) * 1.4142135623730)
return angleRand
end
function SWEP:IsShotgun(base)
if base then
return self:GetBaseValue("Num") > 1 and !self:GetBaseValue("NotShotgun")
else
return self:GetValue("Num") > 1 and !self:GetValue("NotShotgun")
end
end
function SWEP:GetJamChance(base)
local valfunc = base and self.GetBaseValue or self.GetValue
local factor = valfunc(self, "JamFactor")
if factor <= 0 or !TacRP.ConVars["can_jam"]:GetBool() then return 0 end
local default = TacRP.AmmoJamMSB[self:GetAmmoType(base)] or 15
local msb = (valfunc(self, "JamBaseMSB") or default) / math.sqrt(factor)
return 1 / msb
end
function SWEP:GetRPM(base, fm)
fm = fm or self:GetCurrentFiremode()
local valfunc = base and self.GetBaseValue or self.GetValue
local rpm = valfunc(self, "RPM")
if fm == 1 then
rpm = rpm * valfunc(self, "RPMMultSemi")
elseif fm < 0 then
rpm = rpm * valfunc(self, "RPMMultBurst")
end
return rpm
end

View File

@@ -0,0 +1,143 @@
function SWEP:GetIsSprinting()
local owner = self:GetOwner()
if !owner:IsValid() or owner:IsNPC() or owner:IsNextBot() then
return false
end
if self:CanShootInSprint() then return false end
local walkspeed = owner:GetWalkSpeed()
local runspeed = owner:GetRunSpeed()
if owner.TacRP_SprintBlock then return false end
if owner:GetNWBool("TacRPChargeState", false) then return true end
if owner:GetNWBool("SlidingAbilityIsSliding", false) then return false end
if TTT2 then
if SPRINT and SPRINT:IsSprinting(owner) then
return true
else
return owner.isSprinting == true and (owner.sprintProgress or 0) > 0 and owner:KeyDown(IN_SPEED) and !owner:Crouching() and owner:OnGround()
end
end
-- TTT sets runspeed to curspeed, so this will disable it unless sprint addons exist (who ideally sets runspeed. i didn't check)
if runspeed <= walkspeed then return false end
if !owner.TacRP_Moving then return false end -- Don't check IN_ move keys because 1) controllers and 2) bots
if !owner:KeyDown(IN_SPEED) then return false end -- SetButtons does not seem to affect this?
local curspeed = owner:GetVelocity():Length()
if curspeed <= 0 then return false end
if !owner:OnGround() then return false end
if self:GetOwner():GetInfoNum("tacrp_aim_cancels_sprint", 0) > 0 and self:GetScopeLevel() > 0 then return false end
return true
end
function SWEP:ShouldLowerWeapon()
local owner = self:GetOwner()
if !owner:IsValid() or owner:IsNPC() or owner:IsNextBot() then
return false
end
if TacRP.ConVars["sprint_counts_midair"]:GetBool() and owner:GetMoveType() != MOVETYPE_NOCLIP and !owner:IsOnGround() then
return true
end
if self:DoForceSightsBehavior() and self:GetScopeLevel() == 0 and !self:GetInBipod() and self:GetBlindFireMode() == TacRP.BLINDFIRE_NONE then
return true
end
return false
end
function SWEP:CanStopSprinting()
local owner = self:GetOwner()
if !owner:IsValid() or owner:IsNPC() or owner:IsNextBot() then
return false
end
if TacRP.ConVars["sprint_counts_midair"]:GetBool() and owner:GetMoveType() != MOVETYPE_NOCLIP and !owner:OnGround() and !self:GetReloading() then
return false
end
if owner:GetNWBool("TacRPChargeState", false) then
return false
end
return true
end
function SWEP:GetSprintDelta()
return self:GetSprintAmount()
end
function SWEP:EnterSprint()
if !self:CanShootInSprint() then
self:ToggleBlindFire(TacRP.BLINDFIRE_NONE)
end
if !self:CanReloadInSprint() and self:GetReloading() then
-- use clip1 to check for whether the up-in has happened. if so, do not cancel (can't have you cancel the animation *that* easily)
-- this causes fringe cases related to maniuplating magazine sizes but shouldn't be abusable
if self:Clip1() < self:GetMaxClip1() then
self:CancelReload(true)
-- self:Idle()
end
end
self:ScopeToggle(0)
self:SetShouldHoldType()
end
function SWEP:ExitSprint()
local amt = self:GetSprintAmount()
self:SetSprintLockTime(CurTime() + (self:GetValue("SprintToFireTime") * amt))
self:SetShouldHoldType()
end
SWEP.LastWasSprinting = false
function SWEP:ThinkSprint()
local sprinting = self:GetIsSprinting() or self:GetSafe()
local amt = self:GetSprintAmount()
if self.LastWasSprinting and !sprinting then
self:ExitSprint()
elseif !self.LastWasSprinting and sprinting then
self:EnterSprint()
end
self.LastWasSprinting = sprinting
if IsFirstTimePredicted() or game.SinglePlayer() then
if (sprinting or (self:ShouldLowerWeapon() and !self:DoForceSightsBehavior())) and !self:GetInBipod() then
amt = math.Approach(amt, 1, FrameTime() / self:GetValue("SprintToFireTime"))
else
amt = math.Approach(amt, 0, FrameTime() / self:GetValue("SprintToFireTime"))
end
end
self:SetSprintAmount(amt)
end
function SWEP:CanShootInSprint(base)
if !TacRP.ConVars["sprint_lower"]:GetBool() and !self:DoForceSightsBehavior() then return true end
if base then
return self:GetBaseValue("ShootWhileSprint")
else
return self:GetValue("ShootWhileSprint")
end
end
function SWEP:CanReloadInSprint(base)
return TacRP.ConVars["sprint_reload"]:GetBool()
end
function SWEP:DoForceSightsBehavior()
return TacRP.ConVars["sightsonly"]:GetBool() and self:GetValue("Scope")
end

View File

@@ -0,0 +1,239 @@
SWEP.StatCache = {}
SWEP.HookCache = {}
SWEP.StatScoreCache = {} -- used by cust menu
SWEP.MiscCache = {}
SWEP.ExcludeFromRawStats = {
["FullName"] = true,
["PrintName"] = true,
["Description"] = true,
}
SWEP.IntegerStats = {
["ClipSize"] = true,
["Num"] = true,
}
SWEP.AllowNegativeStats = {
["RecoilKick"] = true,
}
function SWEP:InvalidateCache()
self.StatCache = {}
self.HookCache = {}
self.StatScoreCache = {}
self.MiscCache = {}
self.RecoilPatternCache = {}
self.AutoSightPos = nil
self.AutoSightAng = nil
end
function SWEP:RunHook(val, data)
if !self.HookCache[val] then
self.HookCache[val] = {}
if self:GetTable()[val] then
table.insert(self.HookCache[val], self:GetTable()[val])
end
for slot, slottbl in pairs(self.Attachments) do
if !slottbl.Installed then continue end
local atttbl = TacRP.GetAttTable(slottbl.Installed)
if atttbl[val] then
table.insert(self.HookCache[val], atttbl[val])
end
end
end
for _, chook in pairs(self.HookCache[val]) do
local d = chook(self, data)
if d != nil then
data = d
end
end
data = hook.Run("TacRP_" .. val, self, data) or data
return data
end
function SWEP:GetBaseValue(val)
local stat = self:GetTable()[val]
local b = TacRP.GetBalanceMode()
if b > 0 and self.BalanceStats != nil then
if TacRP.BalanceDefaults[b] and TacRP.BalanceDefaults[b][val] != nil then
stat = TacRP.BalanceDefaults[b][val]
end
for j = b, 1, -1 do
if self.BalanceStats[b] and self.BalanceStats[b][val] != nil then
stat = self.BalanceStats[b][val]
break
end
end
end
if isnumber(stat) then
if self.IntegerStats[val] then
stat = math.ceil(stat)
end
if !self.AllowNegativeStats[val] then
stat = math.max(stat, 0)
end
end
return stat
end
function SWEP:GetValue(val, static, invert)
local cachei = invert and 2 or 1
if static == nil then
static = self.StaticStats
end
local stat = nil
-- Generate a cache if it doesn't exist already
if !self.StatCache[val] or !self.StatCache[val][cachei] then
self.StatCache[val] = self.StatCache[val] or {}
stat = self:GetBaseValue(val)
local modifiers = {
["stat"] = nil, -- return this unless hook is set
["hook"] = nil, -- if set, always call hook and use the following values
["func"] = {}, -- modifying functions
["set"] = stat, -- override and no prefix
["prio"] = 0, -- override priority
["add"] = 0,
["mul"] = 1,
}
-- local priority = 0
if !self.ExcludeFromRawStats[val] then
for slot, slottbl in pairs(self.Attachments) do
if !slottbl.Installed then continue end
local atttbl = TacRP.GetAttTable(slottbl.Installed)
local att_priority = atttbl["Priority_" .. val] or 1
if atttbl[val] != nil and att_priority > modifiers.prio then
-- stat = atttbl[val]
-- priority = att_priority
modifiers.set = atttbl[val]
modifiers.prio = att_priority
end
end
end
for slot, slottbl in pairs(self.Attachments) do
if !slottbl.Installed then continue end
local atttbl = TacRP.GetAttTable(slottbl.Installed)
local att_priority = atttbl["Override_Priority_" .. val] or 1
if atttbl["Override_" .. val] != nil and att_priority > modifiers.prio then
-- stat = atttbl["Override_" .. val]
-- priority = att_priority
modifiers.set = atttbl["Override_" .. val]
modifiers.prio = att_priority
end
if atttbl["Add_" .. val] then -- isnumber(stat) and
-- stat = stat + atttbl["Add_" .. val] * (invert and -1 or 1)
modifiers.add = modifiers.add + atttbl["Add_" .. val] * (invert and -1 or 1)
end
if atttbl["Mult_" .. val] then -- isnumber(stat) and
if invert then
-- stat = stat / atttbl["Mult_" .. val]
modifiers.mul = modifiers.mul / atttbl["Mult_" .. val]
else
-- stat = stat * atttbl["Mult_" .. val]
modifiers.mul = modifiers.mul * atttbl["Mult_" .. val]
end
end
if atttbl["Func_" .. val] then
table.insert(modifiers.func, atttbl["Func_" .. val])
end
end
if isfunction(self["Func_" .. val]) then
table.insert(modifiers.func, self["Func_" .. val])
end
-- Check for stat hooks. If any exist, we must call it whenever we try to get the stat.
-- Cache this check so we don't unnecessarily call hook.Run a million times when nobody wants to hook us.
if table.Count(hook.GetTable()["TacRP_Stat_" .. val] or {}) > 0 then
modifiers.hook = true
end
-- Calculate the final value
if isnumber(modifiers.set) then
modifiers.stat = (modifiers.set + modifiers.add) * modifiers.mul
if self.IntegerStats[val] then
modifiers.stat = math.ceil(modifiers.stat)
end
if !self.AllowNegativeStats[val] then
modifiers.stat = math.max(modifiers.stat, 0)
end
else
modifiers.stat = modifiers.set
end
-- Cache our final value, presence of hooks, and summed modifiers
self.StatCache[val][cachei] = modifiers
end
local cache = self.StatCache[val][cachei]
if !static and (cache.hook or #cache.func > 0) then
-- Run the hook
-- Hooks are expected to modify "set", "prio", "add" and "mul", so we can do all calculations in the right order.
local modifiers = {set = nil, prio = 0, add = 0, mul = 1}
if #cache.func > 0 then
for _, f in ipairs(cache.func) do
f(self, modifiers)
end
end
if cache.hook then
hook.Run("TacRP_Stat_" .. val, self, modifiers)
if !istable(modifiers) then modifiers = {set = nil, prio = 0, add = 0, mul = 1} end -- some hook isn't cooperating!
end
if modifiers.prio > cache.prio then
stat = modifiers.set
else
stat = cache.set
end
if isnumber(stat) then
if invert then
stat = (stat - modifiers.add - cache.add) / modifiers.mul / cache.mul
else
stat = (stat + modifiers.add + cache.add) * modifiers.mul * cache.mul
end
if self.IntegerStats[val] then
stat = math.ceil(stat)
end
if !self.AllowNegativeStats[val] then
stat = math.max(stat, 0)
end
end
else
stat = cache.stat
end
return stat
end

View File

@@ -0,0 +1,134 @@
function SWEP:GetSwayAmount(pure)
if self:GetOwner():IsNPC() then return 0 end
local sway = self:GetValue("Sway")
local d = self:GetSightDelta() - (self:GetPeeking() and self:GetValue("PeekPenaltyFraction") or 0)
sway = Lerp(d, sway, self:GetValue("ScopedSway"))
if self:GetBreath() < 1 then
sway = sway + (1 * (1 - self:GetBreath()) * (self:GetOutOfBreath() and 1 or 0.5))
end
sway = Lerp(self:GetHoldBreathAmount() ^ 0.75, sway, 0)
if self:GetBlindFire() then
sway = sway + self:GetValue("BlindFireSway")
end
if self:GetOwner():Crouching() and !(self:GetOwner():KeyDown(IN_FORWARD) or self:GetOwner():KeyDown(IN_MOVELEFT) or self:GetOwner():KeyDown(IN_MOVERIGHT) or self:GetOwner():KeyDown(IN_BACK)) then
sway = sway * self:GetValue("SwayCrouchMult")
end
if !pure then
sway = sway + self:GetForcedSwayAmount()
end
if self:GetValue("Bipod") then
local f = self:Curve(math.Clamp((CurTime() - self.LastBipodTime) / 0.15, 0, 1))
if self:GetInBipod() then
sway = Lerp(f, sway, 0)
else
sway = Lerp(f, 0, sway)
end
end
return sway
end
function SWEP:GetForcedSwayAmount()
local sway = 0
if self:GetOwner():GetNWFloat("TacRPGasEnd", 0) > CurTime() then
sway = sway + TacRP.ConVars["gas_sway"]:GetFloat() * Lerp(self:GetSightAmount(), 1, 0.25) * math.Clamp((self:GetOwner():GetNWFloat("TacRPGasEnd") - CurTime()) / 2, 0, 1)
end
sway = sway + (hook.Run("TacRP_GetForcedSway", self, self:GetOwner()) or 0)
return sway
end
function SWEP:GetSwayAngles()
local swayamt = self:IsSwayEnabled() and self:GetSwayAmount() or self:GetForcedSwayAmount()
local swayspeed = 1
if swayamt <= 0 then return Angle(0, 0, 0) end
local ct = CLIENT and UnPredictedCurTime() or CurTime()
local ang = Angle(math.sin(ct * 0.6 * swayspeed) + (math.cos(ct * 2) * 0.5), math.sin(ct * 0.4 * swayspeed) + (math.cos(ct * 1.6) * 0.5), 0)
ang = ang * swayamt
return ang
end
function SWEP:IsSwayEnabled()
return TacRP.ConVars["sway"]:GetBool()
end
function SWEP:ThinkHoldBreath()
local owner = self:GetOwner()
if !owner:IsPlayer() then return end
local ft = FrameTime()
if self:HoldingBreath() then
self:SetBreath(self:GetBreath() - ft * (self:GetBreathDrain() * (self:HasOptic() and 1 or 0.75) * (self:GetRecoilAmount() > 0 and 1.5 or 1)))
if self:GetBreath() <= 0 then
self:SetOutOfBreath(true)
self:SetHoldingBreath(false)
end
if self:GetHoldBreathAmount() < 1 then
self:SetHoldBreathAmount(math.min(1, self:GetHoldBreathAmount() + ft * self:GetBreathSpeed()))
end
else
if self:GetHoldBreathAmount() > 0 then
self:SetHoldBreathAmount(math.max(0, self:GetHoldBreathAmount() - ft * self:GetBreathSpeed() * 2))
end
if self:GetOutOfBreath() and self:GetBreath() >= 1 then
self:SetOutOfBreath(false)
end
self:SetBreath(math.min(1, self:GetBreath() + ft * self:GetValue("BreathRecovery") * (self:GetOutOfBreath() and 0.2 or 0.25)))
end
end
function SWEP:CanHoldBreath()
return self:GetValue("Scope") and TacRP.ConVars["sway"]:GetBool() and self:GetScopeLevel() > 0 and !self:GetReloading()
end
function SWEP:NotOutOfBreath()
return self:GetBreath() > 0 and !self:GetOutOfBreath()
end
function SWEP:HoldingBreath()
local holding = self:GetOwner():KeyDown(IN_SPEED) or self:GetOwner():KeyDown(IN_RUN)
if self:GetOwner():GetInfoNum("tacrp_toggleholdbreath", 0) == 1 then
if self:GetOwner():KeyPressed(IN_SPEED) or self:GetOwner():KeyPressed(IN_RUN) then
self:SetHoldingBreath(!self:GetHoldingBreath())
end
else
self:SetHoldingBreath(holding)
end
lastpressed = holding
return self:CanHoldBreath() and self:GetSightAmount() >= 1 and self:NotOutOfBreath() and self:GetHoldingBreath()
end
function SWEP:GetBreathDrain()
if self.MiscCache["breath_cost"] == nil then
self.MiscCache["breath_cost"] = (math.Clamp(self:GetValue("ScopedSway"), 0.1, 0.3) ^ 0.75) * (1 - 0.3 * math.Clamp((4 - 90 / self:GetValue("ScopeFOV")) / 3, 0, 1))
end
return self.MiscCache["breath_cost"] * self:GetValue("BreathDrain")
end
function SWEP:GetBreathSpeed()
if self.MiscCache["breath_rate"] == nil then
self.MiscCache["breath_rate"] = (math.Clamp(self:GetValue("ScopedSway"), 0.1, 0.5) ^ 0.5) / 0.3 + (0.5 * math.Clamp((4 - 90 / self:GetValue("ScopeFOV")) / 3, 0, 1))
end
return self.MiscCache["breath_rate"]
end

View File

@@ -0,0 +1,146 @@
function SWEP:Think()
local owner = self:GetOwner()
local stop = self:RunHook("Hook_PreThink")
if stop then return end
local cfm = self:GetCurrentFiremode()
if self:GetValue("RunawayBurst") and cfm < 0 then
if self:GetBurstCount() >= -cfm then
self:SetBurstCount(0)
self:SetNextPrimaryFire(CurTime() + self:GetValue("PostBurstDelay"))
elseif self:GetBurstCount() > 0 and self:GetBurstCount() < -cfm then
self:PrimaryAttack()
end
else
if (owner:KeyReleased(IN_ATTACK) or (cfm < 0 and self:GetBurstCount() >= -cfm)) then
if cfm < 0 and self:GetBurstCount() > 1 then
if !self:GetValue("AutoBurst") then
self.Primary.Automatic = false
end
local add = 0
if self:GetBurstCount() >= -cfm then
add = 60 / self:GetValue("RPM")
end
self:SetNextPrimaryFire(CurTime() + self:GetValue("PostBurstDelay") + add)
end
self:SetBurstCount(0)
end
end
if self:GetPatternCount() > 0 and (self:GetRecoilAmount() == 0 or self:GetReloading()) then
self:SetPatternCount(0)
end
if owner:KeyPressed(TacRP.IN_CUSTOMIZE) then
if self:GetScopeLevel() == 0 then
self:ToggleCustomize(!self:GetCustomize())
else
if !self:GetValue("AlwaysPeek") then
local shouldpeek = !self:GetPeeking()
if owner:GetInfoNum("tacrp_togglepeek", 0) == 0 then
shouldpeek = true
end
self:SetPeeking(shouldpeek)
if self:GetSightAmount() > 0 then
self:SetLastScopeTime(CurTime())
end
end
end
elseif !self:GetValue("AlwaysPeek") and owner:GetInfoNum("tacrp_togglepeek", 0) == 0 and self:GetPeeking() and owner:KeyReleased(TacRP.IN_CUSTOMIZE) then
self:SetPeeking(false)
if self:GetSightAmount() > 0 then
self:SetLastScopeTime(CurTime())
end
end
if owner:KeyPressed(TacRP.IN_TACTICAL) then
self:ToggleTactical()
end
self:ThinkRecoil()
self:ThinkSprint()
self:ThinkGrenade()
self:ThinkReload()
self:ThinkSights()
self:ThinkFreeAim()
self:ThinkBlindFire()
self:ProcessTimers()
self:ThinkLockOn()
self:ThinkHoldBreath()
if self:GetValue("Melee") and self:GetOwner():KeyPressed(TacRP.IN_MELEE) then
self:Melee()
return
end
if IsValid(self:GetOwner()) and self:GetOwner():IsPlayer() and self:GetValue("TacticalThink") and self:GetTactical() then
self:GetValue("TacticalThink")(self)
end
-- if IsValid(self:GetOwner()) and self:GetTactical() and self:GetValue("Minimap") and (SERVER and !game.SinglePlayer()) and (self.NextRadarBeep or 0) < CurTime() then
-- self.NextRadarBeep = CurTime() + 1.5
-- local f = RecipientFilter()
-- f:AddPVS(self:GetPos())
-- f:RemovePlayer(self:GetOwner())
-- local s = CreateSound(self, "plats/elevbell1.wav", f)
-- s:SetSoundLevel(75)
-- s:PlayEx(0.25, 105)
-- end
if self:GetJammed() and !self:StillWaiting() and TacRP.ConVars["jam_autoclear"]:GetBool() then
local t = self:PlayAnimation("jam", 0.75, true, true)
self:GetOwner():DoCustomAnimEvent(PLAYERANIMEVENT_CANCEL_RELOAD, t * 1000)
self:SetJammed(false)
end
if self:GetNextIdle() < CurTime() and (SERVER or !game.SinglePlayer()) then
self:Idle()
end
if self:GetValue("Bipod") and self:GetInBipod() and !self:CanBipod() then
self:ExitBipod()
end
if CLIENT and (IsFirstTimePredicted() or game.SinglePlayer()) then
self:ThinkNearWall()
if IsValid(self.MuzzleLight) then
if (self.MuzzleLightEnd or 0) < UnPredictedCurTime() then
self.MuzzleLight:Remove()
self.MuzzleLight = nil
else
self.MuzzleLight:SetBrightness( math.Remap( UnPredictedCurTime(), self.MuzzleLightStart, self.MuzzleLightEnd, self.MuzzleLightBrightness, 0 ) )
self.MuzzleLight:SetFOV( math.Remap( UnPredictedCurTime(), self.MuzzleLightStart, self.MuzzleLightEnd, self.MuzzleLightFOV, 60 ) )
self.MuzzleLight:Update()
end
end
if !self.LoadedPreset then
self.LoadedPreset = true
if TacRP.ConVars["autosave"]:GetBool() and TacRP.ConVars["free_atts"]:GetBool() then
self:LoadPreset()
-- self:DoDeployAnimation()
end
end
self:CanBipod()
end
self:RunHook("Hook_PostThink")
end

View File

@@ -0,0 +1,51 @@
local tick = 0
function SWEP:InitTimers()
self.ActiveTimers = {} -- { { time, id, func } }
end
function SWEP:SetTimer(time, callback, id)
if !IsFirstTimePredicted() then return end
table.insert(self.ActiveTimers, { time + CurTime(), id or "", callback })
end
function SWEP:TimerExists(id)
for _, v in pairs(self.ActiveTimers) do
if v[2] == id then return true end
end
return false
end
function SWEP:KillTimer(id)
local keeptimers = {}
for _, v in pairs(self.ActiveTimers) do
if v[2] != id then table.insert(keeptimers, v) end
end
self.ActiveTimers = keeptimers
end
function SWEP:KillTimers()
self.ActiveTimers = {}
end
function SWEP:ProcessTimers()
local keeptimers, UCT = {}, CurTime()
if CLIENT and UCT == tick then return end
if !self.ActiveTimers then self:InitTimers() end
for _, v in pairs(self.ActiveTimers) do
if v[1] <= UCT then v[3]() end
end
for _, v in pairs(self.ActiveTimers) do
if v[1] > UCT then table.insert(keeptimers, v) end
end
self.ActiveTimers = keeptimers
end

View File

@@ -0,0 +1,146 @@
function SWEP:OnRestore()
end
function SWEP:GetHeadshotMultiplier(victim, dmginfo)
return 1 -- Hey hey hey, don't forget about me!!!
end
function SWEP:IsEquipment()
return WEPS.IsEquipment(self)
end
SWEP.IsSilent = false
-- The OnDrop() hook is useless for this as it happens AFTER the drop. OwnerChange
-- does not occur when a drop happens for some reason. Hence this thing.
function SWEP:PreDrop()
if SERVER and IsValid(self:GetOwner()) and self.Primary.Ammo != "none" and self.Primary.Ammo != "" then
local ammo = self:Ammo1()
-- Do not drop ammo if we have another gun that uses this type
for _, w in ipairs(self:GetOwner():GetWeapons()) do
if IsValid(w) and w != self and w:GetPrimaryAmmoType() == self:GetPrimaryAmmoType() then
ammo = 0
end
end
self.StoredAmmo = ammo
if ammo > 0 then
self:GetOwner():RemoveAmmo(ammo, self.Primary.Ammo)
end
end
end
function SWEP:DampenDrop()
-- For some reason gmod drops guns on death at a speed of 400 units, which
-- catapults them away from the body. Here we want people to actually be able
-- to find a given corpse's weapon, so we override the velocity here and call
-- this when dropping guns on death.
local phys = self:GetPhysicsObject()
if IsValid(phys) then
phys:SetVelocityInstantaneous(Vector(0,0,-75) + phys:GetVelocity() * 0.001)
phys:AddAngleVelocity(phys:GetAngleVelocity() * -0.99)
end
end
SWEP.StoredAmmo = 0
-- Picked up by player. Transfer of stored ammo and such.
function SWEP:Equip(newowner)
if SERVER then
if self:IsOnFire() then
self:Extinguish()
end
self.fingerprints = self.fingerprints or {}
if !table.HasValue(self.fingerprints, newowner) then
table.insert(self.fingerprints, newowner)
end
if newowner:GetActiveWeapon() != self and self:GetValue("HolsterVisible") then
net.Start("TacRP_updateholster")
net.WriteEntity(self:GetOwner())
net.WriteEntity(self)
net.Broadcast()
end
end
if SERVER and IsValid(newowner) and self.Primary.ClipMax and self.StoredAmmo > 0 and self.Primary.Ammo != "none" and self.Primary.Ammo != "" then
local ammo = newowner:GetAmmoCount(self.Primary.Ammo)
local given = math.min(self.StoredAmmo, self.Primary.ClipMax - ammo)
newowner:GiveAmmo(given, self.Primary.Ammo)
self.StoredAmmo = 0
end
self:SetHolsterTime(0)
self:SetHolsterEntity(NULL)
self:SetReloadFinishTime(0)
end
-- other guns may use this function to setup stuff
function SWEP:TTTBought(buyer)
end
function SWEP:WasBought(buyer)
if buyer:GetActiveWeapon() != self and self:GetValue("HolsterVisible") then
net.Start("TacRP_updateholster")
net.WriteEntity(self:GetOwner())
net.WriteEntity(self)
net.Broadcast()
end
self:TTTBought(buyer)
end
function SWEP:TTT_PostAttachments()
end
function SWEP:TTT_Init()
if engine.ActiveGamemode() != "terrortown" then return end
if SERVER then
self.fingerprints = {}
local att_chance = TacRP.ConVars["ttt_atts_random"]:GetFloat()
local att_max = TacRP.ConVars["ttt_atts_max"]:GetFloat()
local added = 0
if att_chance > 0 then
for i, slot in pairs(self.Attachments) do
if math.random() > att_chance then continue end
local atts = TacRP.GetAttsForCats(slot.Category or "", self)
local ind = math.random(1, #atts)
slot.Installed = atts[ind]
added = added + 1
if att_max > 0 and added >= att_max then break end
end
self:InvalidateCache()
self:SetBaseSettings()
if added > 0 then
self:NetworkWeapon()
end
end
end
if self.PrimaryGrenade then
self.Primary.ClipMax = 1
return
end
self.Primary.ClipMax = TacRP.TTTAmmoToClipMax[string.lower(self.AmmoTTT or self.Ammo)] or self.Primary.ClipSize * 2
self:SetClip1(self.Primary.ClipSize)
self.GaveDefaultAmmo = true
end
--- TTT2 uses this to populate custom convars in the equip menu
function SWEP:AddToSettingsMenu(parent)
end

View File

@@ -0,0 +1,91 @@
function SWEP:SanityCheck()
if !IsValid(self) then return false end
if !IsValid(self:GetOwner()) then return false end
if !IsValid(self:GetVM()) then return false end
end
function SWEP:GetVM()
if !IsValid(self:GetOwner()) or !self:GetOwner():IsPlayer() then return end
return self:GetOwner():GetViewModel()
end
function SWEP:Curve(x)
return 0.5 * math.cos((x + 1) * math.pi) + 0.5
end
SWEP.LastSysTime = SysTime()
function SWEP:DeltaSysTime()
local ret = (SysTime() - (self.LastSysTime or SysTime())) * GetConVar("host_timescale"):GetFloat()
return ret
end
function SWEP:IsAnimLocked()
return self:GetAnimLockTime() > CurTime()
end
function SWEP:ChooseSound(tbl)
if !istable(tbl) then return tbl end
tbl.BaseClass = nil -- lua tables lel
return tbl[math.random(1, #tbl)]
end
function SWEP:OnReloaded()
self:InvalidateCache()
self:SetBaseSettings()
hook.Run("TacRP_WeaponReloaded", self)
end
function SWEP:DoLowerIrons()
if self:GetValue("Holosight") or self:GetValue("ScopeOverlay") then return false end
local i = TacRP.ConVars["irons_lower"]:GetInt()
return i == 2 or (i == 1 and engine.ActiveGamemode() == "terrortown")
end
function SWEP:DoProceduralIrons()
local i = TacRP.ConVars["irons_procedural"]:GetInt()
return self:GetValue("ProceduralIronFire") and (i == 2 or (i == 1 and self:GetValue("Holosight"))) --and (!self.LastShot or self:Clip1() > 1)
end
function SWEP:CountAttachments()
local count = 0
for k, v in ipairs(self.Attachments) do
if v.Installed then count = count + 1 end
end
return count
end
function SWEP:GetMaxClip1()
return self:GetCapacity()
end
function SWEP:IsDamageConstant(base)
local valfunc = base and self.GetBaseValue or self.GetValue
return valfunc(self, "Damage_Min") == valfunc(self, "Damage_Max")
end
function SWEP:GetPingOffsetScale()
if game.SinglePlayer() then return 0 end
return (self:GetOwner():Ping() - 5) / 1000
end
function SWEP:ScaleFOVByWidthRatio(fovDegrees, ratio)
local halfAngleRadians = fovDegrees * (0.5 * math.pi / 180)
local t = math.tan(halfAngleRadians)
t = t * ratio
local retDegrees = (180 / math.pi) * math.atan(t)
return retDegrees * 2
end
function SWEP:WidescreenFix(target)
return self:ScaleFOVByWidthRatio(target, ((ScrW and ScrW() or 4) / (ScrH and ScrH() or 3)) / (4 / 3))
end
function SWEP:UseAltRecoil(base)
local valfunc = base and self.GetBaseValue or self.GetValue
if valfunc(self, "AlwaysAltRecoil") then return true end
if valfunc(self, "NeverAltRecoil") then return false end
return TacRP.ConVars["altrecoil"]:GetBool()
end

View File

@@ -0,0 +1,356 @@
local customizedelta = 0
local sightdelta = 0
local sprintdelta = 0
local peekdelta = 0
local bipoddelta = 0
local blindfiredelta, blindfiredeltaleft, blindfiredeltaright, blindfiredeltakys = 0, 0, 0, 0
local freeaim_p, freeaim_y = 0, 0
local nearwalldelta = 0
local angle_zero = Angle(0, 0, 0)
local vector_origin = Vector(0, 0, 0)
local peekvector = Vector(0, 0, -2)
local m_appor = math.Approach
local f_lerp = function(dlt, from, to) return from + (to - from) * dlt end
local function ApproachMod(usrobj, to, dlt)
usrobj[1] = m_appor(usrobj[1], to[1], dlt)
usrobj[2] = m_appor(usrobj[2], to[2], dlt)
usrobj[3] = m_appor(usrobj[3], to[3], dlt)
end
local function LerpMod(usrobj, to, dlt, clamp_ang)
usrobj[1] = f_lerp(dlt, usrobj[1], to[1])
usrobj[2] = f_lerp(dlt, usrobj[2], to[2])
usrobj[3] = f_lerp(dlt, usrobj[3], to[3])
if clamp_ang then
for i = 1, 3 do usrobj[i] = math.NormalizeAngle(usrobj[i]) end
end
end
SWEP.BenchPos = SWEP.BenchPos or Vector(0, 0, 0)
SWEP.BenchAng = SWEP.BenchAng or Angle(0, 0, 0)
SWEP.ViewModelPos = Vector(0, 0, 0)
SWEP.ViewModelAng = Angle(0, 0, 0)
function SWEP:GetViewModelPosition(pos, ang)
if !IsValid(self:GetOwner()) then
return Vector(0, 0, 0), Angle(0, 0, 0)
end
if TacRP.ConVars["dev_benchgun"]:GetBool() then
return self.BenchPos, self.BenchAng
end
self.BenchPos = pos
self.BenchAng = ang
local vm = self:GetOwner():GetViewModel()
local FT = self:DeltaSysTime() -- FrameTime()
local RFT = RealFrameTime()
ang = ang - (self:GetOwner():GetViewPunchAngles() * 0.5)
local oldang = Angle(0, 0, 0)
oldang:Set(ang)
local offsetpos = Vector(self.PassivePos)
local offsetang = Angle(self.PassiveAng)
local extra_offsetpos = Vector(0, 0, 0)
local extra_offsetang = Angle(0, 0, 0)
-- local cor_val = (self.ViewModelFOV / self:GetShouldFOV())
local cor_val = 0.75
---------------------------------------------
-- Blindfire
---------------------------------------------
local bfmode = self:GetBlindFireMode()
local bfl = bfmode == TacRP.BLINDFIRE_LEFT
local bfr = bfmode == TacRP.BLINDFIRE_RIGHT
local bfs = bfmode == TacRP.BLINDFIRE_KYS
blindfiredelta = math.Approach(blindfiredelta, self:GetBlindFire() and 1 or 0, FT / 0.3)
blindfiredeltaleft = math.Approach(blindfiredeltaleft, bfl and 1 or 0, FT / (bfr and 0.45 or 0.3))
blindfiredeltaright = math.Approach(blindfiredeltaright, bfr and 1 or 0, FT / (bfl and 0.45 or 0.3))
blindfiredeltakys = math.Approach(blindfiredeltakys, bfs and 1 or 0, FT / (bfs and 0.75 or 0.3))
if blindfiredelta > 0 then
local curvedblindfiredelta = self:Curve(blindfiredelta)
local curvedblindfiredeltaleft = self:Curve(blindfiredeltaleft)
local curvedblindfiredeltaright = self:Curve(blindfiredeltaright)
local curvedblindfiredeltakys = self:Curve(blindfiredeltakys)
offsetpos = LerpVector(curvedblindfiredelta, offsetpos, self:GetValue("BlindFirePos"))
offsetang = LerpAngle(curvedblindfiredelta, offsetang, self:GetValue("BlindFireAng"))
if curvedblindfiredeltaleft > 0 then
offsetpos = LerpVector(curvedblindfiredeltaleft, offsetpos, self:GetValue("BlindFireLeftPos"))
offsetang = LerpAngle(curvedblindfiredeltaleft, offsetang, self:GetValue("BlindFireLeftAng"))
end
if curvedblindfiredeltaright > 0 then
offsetpos = LerpVector(curvedblindfiredeltaright, offsetpos, self:GetValue("BlindFireRightPos"))
offsetang = LerpAngle(curvedblindfiredeltaright, offsetang, self:GetValue("BlindFireRightAng"))
end
if curvedblindfiredeltakys > 0 then
offsetpos = LerpVector(curvedblindfiredeltakys, offsetpos, self:GetValue("BlindFireSuicidePos"))
offsetang = LerpAngle(curvedblindfiredeltakys, offsetang, self:GetValue("BlindFireSuicideAng"))
end
end
---------------------------------------------
-- Aiming & Peeking
---------------------------------------------
local ads = self:GetAimDownSightsTime()
if self:GetScopeLevel() > 0 then
if self:GetSprintLockTime() > CurTime() then
ads = ads + self:GetSprintToFireTime()
end
sightdelta = m_appor(sightdelta, 1, FT / ads)
else
sightdelta = m_appor(sightdelta, 0, FT / ads)
end
-- if IsFirstTimePredicted() or game.SinglePlayer() then
if self:GetPeeking() then
peekdelta = m_appor(peekdelta, 1, FT / 0.2)
else
peekdelta = m_appor(peekdelta, 0, FT / 0.2)
end
-- end
local curvedsightdelta = self:Curve(sightdelta)
local curvedpeekdelta = self:Curve(peekdelta)
-- cor_val = Lerp(sightdelta, cor_val, 1)
local ppos = Vector(self:GetValue("PeekPos")) * curvedpeekdelta
local pang = Angle(self:GetValue("PeekAng")) * curvedpeekdelta
if sightdelta > 0 then
local sightpos, sightang = self:GetSightPositions()
if self:DoLowerIrons() then
sightpos = sightpos + LerpVector(curvedpeekdelta, peekvector, vector_origin)
end
LerpMod(offsetpos, sightpos + ppos, curvedsightdelta)
LerpMod(offsetang, sightang + pang, curvedsightdelta, true)
local eepos, eeang = self:GetExtraSightPosition()
local im = self:GetValue("SightMidPoint")
local midpoint = curvedsightdelta * math.cos(curvedsightdelta * (math.pi / 2)) * (1 - curvedpeekdelta)
local joffset = (im and im.Pos or Vector(0, 0, 0) + ppos) * midpoint
local jaffset = (im and im.Ang or Angle(0, 0, 0) + pang) * midpoint
LerpMod(extra_offsetpos, -eepos + joffset, curvedsightdelta)
LerpMod(extra_offsetang, -eeang + jaffset, curvedsightdelta)
end
---------------------------------------------
-- Bipod
---------------------------------------------
local amt = math.Clamp(self:GetBipodPos():Distance(self:GetOwner():EyePos()) / 60, 0.15, 0.3)
bipoddelta = math.Approach(bipoddelta, self:GetInBipod() and 1 or 0, FT / (self:GetInBipod() and 0.4 or amt))
if bipoddelta > 0 then
local curvedbipoddelta = self:Curve(bipoddelta)
pos = LerpVector(math.Clamp(curvedbipoddelta - curvedsightdelta, 0, 1), pos, self:GetBipodPos())
end
---------------------------------------------
-- Procedural Firing
---------------------------------------------
local procdata = self:GetValue("ProceduralIronFire")
if IsValid(vm) and procdata then
local dt = math.max(0, UnPredictedCurTime() - self:GetLastProceduralFireTime() + self:GetPingOffsetScale())
if dt <= procdata.tmax then
self.ProceduralIronCleanup = false
if !(self:GetValue("LastShot") and self:Clip1() == 0) then
for k, v in pairs(procdata.bones or {}) do
local bone = vm:LookupBone(v.bone or "")
if !bone then continue end
local f = 1
if v.t0 == 0 then
f = v.t1 and math.Clamp(1 - dt / v.t1, 0, 1) or 0
else
f = v.t1 and (dt > v.t0 and math.Clamp(1 - (dt - v.t0) / (v.t1 - v.t0), 0, 1) or (dt / v.t0)) or (dt > v.t0 and 1 or (dt / v.t0))
end
if v.pos then
local offset = LerpVector(f, vector_origin, v.pos)
vm:ManipulateBonePosition(bone, offset, false)
end
if v.ang then
local offset = LerpAngle(f, angle_zero, v.ang)
vm:ManipulateBoneAngles(bone, offset, false)
end
end
end
local dtc = math.ease.InQuad(math.Clamp(1 - dt / procdata.t, 0, 1))
if dtc > 0 and procdata.vm_pos then
LerpMod(offsetpos, offsetpos + procdata.vm_pos, dtc)
end
if dtc > 0 and procdata.vm_ang then
LerpMod(offsetang, offsetang + procdata.vm_ang, dtc, true)
end
elseif !self.ProceduralIronCleanup then
self.ProceduralIronCleanup = true
for k, v in pairs(procdata.bones or {}) do
local bone = vm:LookupBone(v.bone or "")
if !bone then continue end
if v.pos then
vm:ManipulateBonePosition(bone, vector_origin, false)
end
if v.ang then
vm:ManipulateBoneAngles(bone, angle_zero, false)
end
end
end
end
---------------------------------------------
-- Free Aim & Sway
---------------------------------------------
local swayang = self:GetSwayAngles()
extra_offsetang.y = extra_offsetang.y - (swayang.p * cor_val)
extra_offsetang.p = extra_offsetang.p + (swayang.y * cor_val)
local idlesway = Lerp(self:GetSightDelta(), 1 / 3, 0)
extra_offsetpos.x = extra_offsetpos.x + (swayang.y * cor_val * idlesway)
extra_offsetpos.z = extra_offsetpos.z + (swayang.p * cor_val * idlesway)
local freeaimang = self:GetFreeAimOffset()
freeaim_p = f_lerp(0.5, freeaim_p, freeaimang.p)
freeaim_y = f_lerp(0.5, freeaim_y, freeaimang.y)
freeaim_p = m_appor(freeaim_p, freeaimang.p, FT)
freeaim_y = m_appor(freeaim_y, freeaimang.y, FT)
extra_offsetang.y = extra_offsetang.y - (freeaim_p * cor_val)
extra_offsetang.p = extra_offsetang.p + (freeaim_y * cor_val)
---------------------------------------------
-- Customization
---------------------------------------------
-- if IsFirstTimePredicted() or game.SinglePlayer() then
if self:GetCustomize() then
customizedelta = m_appor(customizedelta, 1, RealFrameTime() * 1 / 0.15)
else
customizedelta = m_appor(customizedelta, 0, RealFrameTime() * 1 / 0.15)
end
-- end
if customizedelta > 0 then
local curvedcustomizedelta = self:Curve(customizedelta)
LerpMod(offsetpos, self:GetValue("CustomizePos"), curvedcustomizedelta)
LerpMod(offsetang, self:GetValue("CustomizeAng"), curvedcustomizedelta)
LerpMod(extra_offsetang, angle_zero, curvedcustomizedelta, true)
end
---------------------------------------------
-- Sprinting
---------------------------------------------
local stf = self:GetSprintToFireTime()
if self:GetCustomize() or self:GetInBipod() or (!self:GetSafe() and !self.LastWasSprinting and !self:ShouldLowerWeapon()) then
-- not accurate to how sprint progress works but looks much smoother
if self:GetScopeLevel() > 0 and self:GetSprintLockTime() > UnPredictedCurTime() then
stf = stf + self:GetAimDownSightsTime() * 0.5
end
sprintdelta = m_appor(sprintdelta, 0, FT / stf)
self.LastReloadEnd = nil
elseif self:GetReloading() then
if (self.LastWasSprinting or self:ShouldLowerWeapon()) and self:GetEndReload() then
self.LastReloadEnd = self.LastReloadEnd or (self:GetReloadFinishTime() - UnPredictedCurTime())
sprintdelta = 1 - self:Curve((self:GetReloadFinishTime() - UnPredictedCurTime()) / self.LastReloadEnd)
else
sprintdelta = m_appor(sprintdelta, 0, FT / 0.5)
end
else
if self:GetLastMeleeTime() + 0.5 > CurTime() or self:GetStartPrimedGrenadeTime() + 0.8 > CurTime() then
sprintdelta = m_appor(sprintdelta, 0, FT / 0.2)
else
sprintdelta = m_appor(sprintdelta, 1, FT / stf)
end
self.LastReloadEnd = nil
end
local curvedsprintdelta = self:Curve(sprintdelta)
if curvedsprintdelta > 0 then
LerpMod(offsetpos, self:GetValue("SprintPos"), curvedsprintdelta)
LerpMod(offsetang, self:GetValue("SprintAng"), curvedsprintdelta)
LerpMod(extra_offsetang, angle_zero, curvedsprintdelta, true)
local sim = self:GetValue("SprintMidPoint")
local spr_midpoint = curvedsprintdelta * math.cos(curvedsprintdelta * (math.pi / 2))
local spr_joffset = (sim and sim.Pos or Vector(0, 0, 0)) * spr_midpoint
local spr_jaffset = (sim and sim.Ang or Angle(0, 0, 0)) * spr_midpoint
extra_offsetpos:Add(spr_joffset)
extra_offsetang:Add(spr_jaffset)
end
---------------------------------------------
-- Near Walling
---------------------------------------------
nearwalldelta = m_appor(nearwalldelta, self:GetNearWallAmount(), FT / 0.3)
local curvednearwalldelta = self:Curve(nearwalldelta) - customizedelta - sightdelta
if curvednearwalldelta > 0 then
local sprpos = LerpVector(curvednearwalldelta, vector_origin, self:GetValue("NearWallPos"))
local sprang = LerpAngle(curvednearwalldelta, angle_zero, self:GetValue("NearWallAng"))
local pointdir = self:GetOwner():WorldToLocalAngles(self:GetShootDir())
extra_offsetpos:Add(pointdir:Right() * sprpos[2])
extra_offsetpos:Add(pointdir:Forward() * sprpos[1])
extra_offsetpos:Add(pointdir:Up() * sprpos[3])
extra_offsetang:Add(sprang)
end
self.SwayScale = f_lerp(sightdelta, 1, 0.1)
self.BobScale = 0
local speed = 15 * FT * (game.SinglePlayer() and 1 or 2)
LerpMod(self.ViewModelPos, offsetpos, speed)
LerpMod(self.ViewModelAng, offsetang, speed, true)
ApproachMod(self.ViewModelPos, offsetpos, speed * 0.1)
ApproachMod(self.ViewModelAng, offsetang, speed * 0.1)
self.ViewModelAng:Normalize()
pos = pos + (ang:Right() * offsetpos[1])
pos = pos + (ang:Forward() * offsetpos[2])
pos = pos + (ang:Up() * offsetpos[3])
ang:RotateAroundAxis(ang:Up(), offsetang[1])
ang:RotateAroundAxis(ang:Right(), offsetang[2])
ang:RotateAroundAxis(ang:Forward(), offsetang[3])
pos = pos + (oldang:Right() * extra_offsetpos[1])
pos = pos + (oldang:Forward() * extra_offsetpos[2])
pos = pos + (oldang:Up() * extra_offsetpos[3])
ang:RotateAroundAxis(oldang:Up(), extra_offsetang[1])
ang:RotateAroundAxis(oldang:Right(), extra_offsetang[2])
ang:RotateAroundAxis(oldang:Forward(), extra_offsetang[3])
pos, ang = self:GetViewModelBob(pos, ang)
pos, ang = self:GetViewModelSway(pos, ang)
self.ViewModelPos = pos
self.ViewModelAng = ang
self.LastSysTime = SysTime()
return pos, ang
end
function SWEP:TranslateFOV(fov)
return fov
end

View File

@@ -0,0 +1,666 @@
// spawnable
SWEP.Spawnable = false
SWEP.AdminOnly = false
// names and stuff
SWEP.PrintName = "Arctic's Tactical RP Base"
SWEP.Category = "[FT] Оружие"
SWEP.Description = ""
SWEP.Description_Quote = nil // Italics, always on last line. Make sure to save some space for it (may overlap)
SWEP.Trivia_Caliber = nil
SWEP.Trivia_Manufacturer = nil
SWEP.Trivia_Year = nil // Production Year
SWEP.Faction = TacRP.FACTION_NEUTRAL // Only used in trivia for now
// Valid values: TacRP.FACTION_NEUTRAL, TacRP.FACTION_COALITION, TacRP.FACTION_MILITIA
SWEP.Credits = nil // Multiline string like Description
SWEP.ViewModel = ""
SWEP.WorldModel = ""
SWEP.ViewModelFOV = 65
SWEP.NoRanger = false
SWEP.NoStatBox = false
SWEP.NPCUsable = true
SWEP.Slot = 1
SWEP.RenderGroup = RENDERGROUP_BOTH
SWEP.BalanceStats = {} // replacement stats for each TacRP.BALANCE_ enum
// What weapon this will replace in TTT if enabled. Use TacRP.TTTReplacePreset presets or define your own
SWEP.TTTReplace = nil // {["weapon_ttt_glock"] = 1} // key is weapon to replace, value is relative weight.
// "ballistics"
SWEP.Damage_Max = 30 // damage at minimum range
SWEP.Damage_Min = 20 // damage at maximum range
SWEP.Range_Min = 256 // distance for which to maintain maximum damage
SWEP.Range_Max = 1024 // distance at which we drop to minimum damage
SWEP.Penetration = 0 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.5 // How good the weapon can penetrate body armor.
SWEP.ArmorBonus = 1 // multiplier on armor damage
SWEP.DamageMultNPC = 1 // Damage multiplier against NPCs and Nextbots
SWEP.DamageType = nil // override damage type
SWEP.ShootEnt = false
SWEP.ShootEntForce = 10000
SWEP.Num = 1
SWEP.TracerNum = 1
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 1.25,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 30000
SWEP.ExplosiveEffect = nil
SWEP.ExplosiveDamage = 0
SWEP.ExplosiveRadius = 0
// misc. shooting
// Firemode system works just like ArcCW
// 2 = full auto
// 1 = semi auto
// 0 = safe
// negative numbers = burst
SWEP.Firemode = 2
SWEP.Firemodes = nil // {1, 2, 0} ...
SWEP.RunawayBurst = false // continue firing until burst is completely expended
SWEP.PostBurstDelay = 0 // only applies to runaway burst guns
SWEP.AutoBurst = false // hold the trigger to keep firing burst after burst
SWEP.RPM = 600
SWEP.RPMMultBurst = 1 // modify RPM while in burst mode
SWEP.RPMMultSemi = 1 // modify RPM while in semi mode
SWEP.Spread = 0.01
SWEP.ShootTimeMult = 1
SWEP.Bipod = false // Weapon can deploy bipod
SWEP.BipodRecoil = 0.35 // Recoil Amount multiplier per shot
SWEP.BipodKick = 0.25 // Recoil Kick multiplier
SWEP.TriggerDelay = 0.0
// SWEP.ShootChance = 1
SWEP.JamWaitTime = 0.3
SWEP.JamFactor = 0 // higher = more frequent jams. no jams at 0
SWEP.JamTakesRound = false // consume ammo on jam
SWEP.JamSkipFix = false // only do dryfire and the initial delay. use on revolvers mostly
SWEP.JamBaseMSB = nil // use this number as the base value instead of being based on ammo.
// Spread penalties are in spread units and are additive
SWEP.MoveSpreadPenalty = 0.01 // spread penalty while travelling at max. 250 u/s
SWEP.MidAirSpreadPenalty = 0.1 // spread penalty for being in the air
SWEP.HipFireSpreadPenalty = 0.02 // spread penalty for not being scoped in
SWEP.ScopedSpreadPenalty = 0 // spread penalty for... being scoped in?
SWEP.BlindFireSpreadPenalty = 0 // spread penalty for blind firing
SWEP.CrouchSpreadPenalty = 0
SWEP.PeekPenaltyFraction = 0.3 // percentage of hipfire penalty to use while peeking in sights
// Technically does not affect recoil at all, but affects spread (now called "bloom")
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 10
SWEP.RecoilResetTime = 0 // time after you stop shooting for recoil to start dissipating
SWEP.RecoilDissipationRate = 2
SWEP.RecoilFirstShotMult = 1 // multiplier for the first shot's recoil amount
SWEP.RecoilSpreadPenalty = 0.001 // extra spread per one unit of recoil
SWEP.RecoilResetInstant = true // Set false to account for RPM.
SWEP.RecoilMultBurst = 0.9 // Affects both "bloom" and recoil kick while current firemode is burst
SWEP.RecoilMultSemi = 0.9 // Affects both "bloom" and recoil kick while current firemode is semi
SWEP.RecoilMultCrouch = 0.85 // Affects both "bloom" and recoil kick while crouched
// Controls alternate bloom behavior, defaults to convar
SWEP.AlwaysAltRecoil = nil
SWEP.NeverAltRecoil = nil
SWEP.RecoilVisualKick = 0.1
SWEP.RecoilKick = 0.25
SWEP.RecoilStability = 0 // Direction of recoil kick, 1 is completely vertical and 0 is 180deg cone
SWEP.RecoilAltMultiplier = 200 // Multiplier to RecoilSpreadPenalty when using alternative recoil mode.
SWEP.ShotgunPelletSpread = 0 // per-pellet spread for shotguns (if enabled). Otherwise just adds to spread
SWEP.NoRecoilPattern = false // set true to not use recoil patterns for this gun
SWEP.RecoilPatternSeed = nil // custom seed. Defaults to weapon class
SWEP.CanBlindFire = true
SWEP.CannotHipFire = false
// lockon
// We're using a new system for lockon now, which doesn't use this system.
// SWEP.LockOnAngle = math.cos(math.rad(5))
SWEP.LockOnTrackAngle = 5
SWEP.LockOnRange = 3500
SWEP.LockOnTime = 1.5
SWEP.ProvideTargetData = true
SWEP.LockOnOutOfSights = false
SWEP.LockOnInSights = false
SWEP.RequireLockOn = false // Cannot shoot without a lock
// handling
SWEP.MoveSpeedMult = 1
SWEP.ShootingSpeedMult = 0.5 // slow down applied while shooting
SWEP.SightedSpeedMult = 0.5
SWEP.MeleeSpeedMult = 0.75
SWEP.MeleeSpeedMultTime = 1 // seconds to apply slow down for
SWEP.ReloadSpeedMult = 1
SWEP.ReloadSpeedMultTime = 0.5 // duration for slowdown to fade out for AFTER RELOAD FINISHES
SWEP.ShootWhileSprint = false
SWEP.AimDownSightsTime = 0.25
SWEP.SprintToFireTime = 0.25 // how long it takes to go from sprinting to shooting
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.HoldTypeCustomize = "slam"
SWEP.HoldTypeNPC = nil
SWEP.HoldTypeSuicide = "pistol"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_AR2
SWEP.GestureBash = ACT_GMOD_GESTURE_MELEE_SHOVE_1HAND
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, 0, 0)
SWEP.SprintAng = Angle(0, 45, 0)
SWEP.SprintPos = Vector(0, 0, 0)
SWEP.BlindFireAng = Angle(0, 15, 0)
SWEP.BlindFirePos = Vector(0, 0, -6)
SWEP.BlindFireLeftAng = Angle(75, 0, 0)
SWEP.BlindFireLeftPos = Vector(8, 14, -12)
SWEP.BlindFireRightAng = Angle(-75, 0, 0)
SWEP.BlindFireRightPos = Vector(-8, 14, -12)
SWEP.BlindFireSuicideAng = Angle(0, 145, 130)
SWEP.BlindFireSuicidePos = Vector(-6, 32, -26)
SWEP.CustomizeAng = Angle(30, 15, 0)
SWEP.CustomizePos = Vector(6, 0, -7)
SWEP.SightAng = Angle(0, 0, 0)
SWEP.SightPos = Vector(0, 1, 1)
SWEP.PeekAng = Angle(0, 0, -7)
SWEP.PeekPos = Vector(3, 2, -1.5)
SWEP.HolsterVisible = false
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(0, 0, 0)
SWEP.HolsterAng = Angle(0, 0, 0)
SWEP.HolsterModel = nil // string, model.
SWEP.SightMidPoint = {
Pos = Vector(-1, 15, -6),
Ang = Angle(0, 0, -45)
}
SWEP.SprintMidPoint = {
Pos = Vector(4, 10, 2),
Ang = Angle(0, -10, -45)
}
SWEP.NearWallPos = Vector(0, 6, 0)
SWEP.NearWallAng = Angle(-3, 5, -5)
// scope
SWEP.Scope = true
SWEP.ScopeOverlay = nil // Material("path/to/overlay")
SWEP.ScopeFOV = 90 / 1.1
SWEP.ScopeLevels = 1 // 2 = like CS:S
SWEP.ScopeHideWeapon = false
SWEP.QuickScopeSpreadPenalty = 0.05
SWEP.QuickScopeTime = 0.2 // amount of time over which to fade out the quickscope spread penalty
// sway
SWEP.Sway = 1
SWEP.ScopedSway = 0.1
SWEP.BlindFireSway = 2
SWEP.SwayCrouchMult = 0.75
SWEP.BreathRecovery = 1
SWEP.BreathDrain = 1
SWEP.FreeAim = true
SWEP.FreeAimMaxAngle = 3.5
SWEP.ShootOffset = Vector(0, 0, 0)
SWEP.ShootOffsetAngle = Angle(0, 0, 0)
// quicknade
SWEP.CanQuickNade = true
SWEP.QuickNadeTimeMult = 1
// melee
SWEP.CanMeleeAttack = true
SWEP.MeleeDamage = 25
SWEP.MeleeAttackTime = 0.8 // time between swings
SWEP.MeleeRange = 96
SWEP.MeleeDamageType = DMG_GENERIC
SWEP.MeleeDelay = 0.25 // delay between swing start and trace
// secondary attack, used on knives
SWEP.Melee2Damage = nil
SWEP.Melee2AttackTime = nil
SWEP.Melee2Range = nil
SWEP.Melee2AttackMissTime = nil
SWEP.Melee2Delay = nil
SWEP.MeleeThrowForce = 3000
// used on knife perks
SWEP.MeleePerkStr = 0.5
SWEP.MeleePerkAgi = 0.5
SWEP.MeleePerkInt = 0.5
// reload
SWEP.AmmoPerShot = 1
SWEP.ClipSize = 30
SWEP.Ammo = "pistol"
SWEP.InfiniteAmmo = false // do not consume reserve ammo
SWEP.SupplyAmmoAmount = false // overrides clipsize/ammo for ammo pickups
SWEP.SupplyLimit = 1 // Multiplier for supply ammo
SWEP.TryUnholster = false // if we have an "unholster" animation use it instead of "deploy"
SWEP.ShotgunReload = false
SWEP.ShotgunThreeload = true // use those stupid 3 shot reload animations
SWEP.ShotgunReloadCompleteStart = false // do not interrupt reload_start and instead wait for it to finish first. used on FP6 animations
SWEP.ShotgunFullCancel = false // Ignore tacrp_reload_sg_cancel and force cancel animation
SWEP.ShotgunNoReverseStart = true // don't reverse starting animation on a non-empty reload
SWEP.ShotgunUpInTime = 0.9 // time after which one round is finished loading
SWEP.ReloadUpInTime = nil // time to restore ammo, if unset restores at end of animation
SWEP.ReloadTimeMult = 1
SWEP.DeployTimeMult = 1
SWEP.HolsterTimeMult = 1
SWEP.UnholsterTimeMult = 1
SWEP.DropMagazineModel = false
SWEP.DropMagazineImpact = "pistol" // available: "pistol", "plastic", "metal", "bullet", "shotgun"
SWEP.DropMagazineAmount = 1
SWEP.DropMagazineTime = 0
SWEP.MidReload = false // allow guns with "midreload" animation to continue reload after holster
SWEP.DefaultBodygroups = "0000000"
SWEP.DefaultWMBodygroups = "0000000"
SWEP.DefaultSkin = 0
SWEP.BulletBodygroups = nil
SWEP.BulletBodygroupsSetAll = false // Set all applicable bullet groups, rather than just the last
/*
{
[1] = {5, 1}
}
*/
SWEP.LoadInTime = 0.25 // how long to replenish the visible "belt" of ammo
SWEP.ShotgunLoadInTime = 0.9 // visual update delay for shotguns
// sounds
SWEP.Sound_Shoot = "^"
SWEP.Sound_Shoot_Silenced = ""
SWEP.Vol_Shoot = 130
SWEP.Pitch_Shoot = 100
SWEP.Loudness_Shoot = 1
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
SWEP.Sound_ScopeIn = ""
SWEP.Sound_MeleeAttack = ""
SWEP.Sound_DryFire = "TacRP/weapons/dryfire_pistol-1.wav"
SWEP.Sound_Jam = "TacRP/malfunction.wav"
SWEP.Sound_BipodDown = "tacrp/bipod_down.wav"
SWEP.Sound_BipodUp = "tacrp/bipod_up.wav"
SWEP.Sound_MeleeSwing = ""
SWEP.Sound_ToggleTactical = "tacrp/firemode.wav"
SWEP.Sound_StartLockOn = "tacrp/check1.wav"
SWEP.Sound_FinishLockOn = "tacrp/locked1.wav"
// effects
SWEP.EffectsAlternate = false // Effects will alternate using L and R attachments.
SWEP.EffectsDoubled = false // Per shot, play effects a second time on the other attachment.
// .qc attachment for muzzle flash and eject when EffectsAlternate is NOT true.
SWEP.QCA_Muzzle = 1
SWEP.QCA_Eject = 2
// .qc attachments when EffectsAlternate is set to true.
SWEP.QCA_MuzzleL = 3
SWEP.QCA_MuzzleR = 4
SWEP.QCA_EjectL = 6
SWEP.QCA_EjectR = 7
// ditto but for worldmodel
SWEP.WM_QCA_Muzzle = 1
SWEP.WM_QCA_Eject = 2
SWEP.WM_QCA_MuzzleL = 1
SWEP.WM_QCA_MuzzleR = 2
SWEP.WM_QCA_EjectL = 3
SWEP.WM_QCA_EjectR = 4
SWEP.MuzzleEffect = "muzzleflash_pistol"
SWEP.EjectEffect = 0 // 1 = pistol, 2 = rifle, 3 = shotgun
SWEP.EjectDelay = 0
SWEP.EjectScale = 1
// anims
// VM:
// idle
// fire
// fire1, fire2...
// dryfire
// melee
// reload
// midreload
// prime_grenade
// throw_grenade
// throw_grenade_underhand
// deploy
// blind_idle
// blind_fire
// blind_fire1, blind_fire2...
// blind_dryfire
// WM:
// attack1
SWEP.AnimationTranslationTable = {
["melee"] = {"melee1", "melee2"},
["jam"] = "midreload"
} // translates ["fire"] = "shoot"; key = translates from, value = translates to
// e.g. you have a "shoot1" sequence and need "fire"
// so ["fire"] = "shoot1"
// can be ["fire"] = {"list", "of", "values"}
SWEP.ProceduralIronFire = nil // procedurally animate the viewmodel and bones when using ironsights
// {
// vm_pos = Vector(0, -0.5, -0.6),
// vm_ang = Angle(0, 2, 0),
// t = 0.2, // duration of vm pos/ang
// tmax = 0.2, // clean up after this time has passed
// bones = {
// {
// bone = "ValveBiped.slide",
// pos = Vector(0, 0, -3), // optional
// ang = Angle(0, 0, 0), // optional
// t0 = 0.05, // duration to reach full movement
// t1 = 0.2, // duration to reset
// },
// },
// }
SWEP.NoHolsterAnimation = false // Will play draw reversed instead
SWEP.LastShot = false
// Use special animation setup for akimbo pistols.
// Does not adjust effects - set AlternatingEffects separately.
SWEP.Akimbo = false
// attachments
SWEP.AttachmentElements = nil
/*
{
["bg_name"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
},
AttPosMods = {
[1] = {
Pos_VM = Vector(),
Pos_WM = Vector(),
Ang_VM = Angle(),
Ang_WM = Angle(),
},
},
SortOrder = 1, // defaults to 1, higher value means process later
}
}
*/
SWEP.Attachments = nil
// {
// [1] = {
// Installed = nil,
// Default = nil, // install this attachment by default
// InstalledElements = "", // single or list of elements to activate when something is installed here
// UnInstalledElements = "",
// Integral = false, // cannot be removed
// Category = "", // single or {"list", "of", "values"}
// Bone = "",
// WMBone = "",
// Pos_VM = Vector(0, 0, 0),
// Pos_WM = Vector(0, 0, 0),
// Ang_VM = Angle(0, 0, 0),
// Ang_WM = Angle(0, 0, 0),
// CapacityMult = 1, // multiply the amount of Capacity this attachment occupies
// }
// }
// boilerplate
SWEP.FreeAim = true
SWEP.ArcticTacRP = true
SWEP.DrawCrosshair = true
SWEP.AccurateCrosshair = true
SWEP.DrawWeaponInfoBox = false
SWEP.UseHands = true
SWEP.Shields = {}
SWEP.CurrentAnimation = ""
SWEP.Primary.Automatic = false
SWEP.Primary.ClipSize = 0
SWEP.Primary.Ammo = ""
SWEP.Primary.DefaultClip = 0
SWEP.Secondary.Automatic = true
SWEP.Secondary.ClipSize = -1
SWEP.Secondary.Ammo = ""
SWEP.Secondary.DefaultClip = 0
SWEP.GaveDefaultAmmo = false
SWEP.BounceWeaponIcon = false
SWEP.SwayScale = 1
SWEP.BobScale = 1
SWEP.LaserColor = Color(255, 0, 0)
SWEP.ActiveEffects = {}
SWEP.PCFs = {}
SWEP.MuzzPCFs = {}
AddCSLuaFile()
local searchdir = "weapons/tacrp_base"
local function autoinclude(dir)
local files, dirs = file.Find(searchdir .. "/*.lua", "LUA")
for _, filename in pairs(files) do
if filename == "shared.lua" then continue end
local luatype = string.sub(filename, 1, 2)
if luatype == "sv" then
if SERVER then
include(dir .. "/" .. filename)
end
elseif luatype == "cl" then
AddCSLuaFile(dir .. "/" .. filename)
if CLIENT then
include(dir .. "/" .. filename)
end
else
AddCSLuaFile(dir .. "/" .. filename)
include(dir .. "/" .. filename)
end
end
for _, path in pairs(dirs) do
autoinclude(dir .. "/" .. path)
end
end
autoinclude(searchdir)
function SWEP:SetupDataTables()
self:NetworkVar("Float", 0, "RecoilAmount")
self:NetworkVar("Float", 1, "AnimLockTime")
self:NetworkVar("Float", 2, "NextIdle")
self:NetworkVar("Float", 3, "LastRecoilTime")
self:NetworkVar("Float", 4, "RecoilDirection")
self:NetworkVar("Float", 5, "SprintAmount")
self:NetworkVar("Float", 6, "SprintLockTime")
self:NetworkVar("Float", 7, "LastScopeTime")
self:NetworkVar("Float", 8, "LastMeleeTime")
self:NetworkVar("Float", 9, "PrimedGrenadeTime")
self:NetworkVar("Float", 10, "StartPrimedGrenadeTime")
self:NetworkVar("Float", 11, "ReloadFinishTime")
self:NetworkVar("Float", 12, "NWSightAmount")
self:NetworkVar("Float", 13, "BlindFireFinishTime")
self:NetworkVar("Float", 14, "HolsterTime")
self:NetworkVar("Float", 15, "NWLastProceduralFireTime")
self:NetworkVar("Float", 16, "NWHoldBreathAmount")
self:NetworkVar("Float", 17, "Breath")
self:NetworkVar("Float", 18, "LockOnStartTime")
self:NetworkVar("Int", 0, "BurstCount")
self:NetworkVar("Int", 1, "ScopeLevel")
self:NetworkVar("Int", 2, "NthShot")
self:NetworkVar("Int", 3, "LoadedRounds")
self:NetworkVar("Int", 4, "Firemode")
self:NetworkVar("Int", 5, "PatternCount")
self:NetworkVar("Bool", 0, "Customize")
self:NetworkVar("Bool", 1, "Reloading")
self:NetworkVar("Bool", 2, "BlindFire")
self:NetworkVar("Bool", 3, "EndReload")
self:NetworkVar("Bool", 4, "PrimedGrenade")
self:NetworkVar("Bool", 5, "Safe")
self:NetworkVar("Bool", 6, "BlindFireLeft")
self:NetworkVar("Bool", 7, "Tactical")
self:NetworkVar("Bool", 8, "Charge")
self:NetworkVar("Bool", 9, "NWPeeking")
self:NetworkVar("Bool", 10, "BlindFireRight") // bleh, but actually less networking load than using an integer (32 bit)
self:NetworkVar("Bool", 11, "Jammed")
self:NetworkVar("Bool", 12, "Ready")
self:NetworkVar("Bool", 13, "InBipod")
self:NetworkVar("Bool", 14, "OutOfBreath")
self:NetworkVar("Bool", 15, "HoldingBreath")
self:NetworkVar("Bool", 16, "LastWasSprinting")
self:NetworkVar("Bool", 17, "EmptyReload")
self:NetworkVar("Angle", 0, "FreeAimAngle")
self:NetworkVar("Angle", 1, "LastAimAngle")
self:NetworkVar("Angle", 2, "BipodAngle")
self:NetworkVar("Vector", 0, "BipodPos")
self:NetworkVar("Entity", 0, "HolsterEntity")
self:NetworkVar("Entity", 1, "CornershotEntity")
self:NetworkVar("Entity", 2, "LockOnEntity")
self:SetFreeAimAngle(Angle())
self:SetLastAimAngle(Angle())
self:SetFiremode(1)
self:SetTactical(true)
self:SetReady(false)
self:SetBreath(1)
self:SetHoldBreathAmount(0)
self:SetLastWasSprinting(false)
self:SetHoldingBreath(false)
self:SetLockOnEntity(NULL)
self:SetLockOnStartTime(0)
end
function SWEP:OnDrop(owner)
if self.PreviousZoom and IsValid(owner) then
owner:SetCanZoom(true)
end
self:SetReady(false)
end
function SWEP:SecondaryAttack()
self:RunHook("Hook_SecondaryAttack")
return
end
local function clunpredictvar(tbl, name, varname, default)
local clvar = "CL_" .. name
tbl[clvar] = default
tbl["Set" .. name] = function(self, v)
if (!game.SinglePlayer() and CLIENT and self:GetOwner() == LocalPlayer()) then self[clvar] = v end
self["Set" .. varname](self, v)
end
tbl["Get" .. name] = function(self)
if (!game.SinglePlayer() and CLIENT and self:GetOwner() == LocalPlayer()) then return self[clvar] end
return self["Get" .. varname](self)
end
end
clunpredictvar(SWEP, "SightAmount", "NWSightAmount", 0)
-- clunpredictvar(SWEP, "SprintAmount", "NWSprintAmount", 0)
clunpredictvar(SWEP, "LastProceduralFireTime", "NWLastProceduralFireTime", 0)
clunpredictvar(SWEP, "HoldBreathAmount", "NWHoldBreathAmount", 0)

View File

@@ -0,0 +1,62 @@
function SWEP:NetworkWeapon(sendto)
net.Start("TacRP_networkweapon")
net.WriteUInt(self:EntIndex(), 13)
for slot, slottbl in pairs(self.Attachments) do
if !slottbl.Installed then net.WriteUInt(0, TacRP.Attachments_Bits) continue end
local atttbl = TacRP.GetAttTable(slottbl.Installed)
net.WriteUInt(atttbl.ID, TacRP.Attachments_Bits)
end
if sendto then
net.Send(sendto)
else
net.SendPVS(self:GetPos())
end
self:InvalidateCache()
self:DoBodygroups(true)
self:DoBodygroups(false)
end
function SWEP:ReceivePreset()
for slot, slottbl in pairs(self.Attachments) do
local attid = net.ReadUInt(TacRP.Attachments_Bits)
if attid == 0 then
if slottbl.Installed then
self:Detach(slot, true)
end
else
local att = TacRP.Attachments_Index[attid]
local atttbl = TacRP.GetAttTable(att)
if !atttbl then continue end
if slottbl.Installed then
self:Detach(slot, true)
end
self:Attach(slot, att, true, true)
if atttbl.OnPresetLoad then
atttbl.OnPresetLoad(self)
end
end
end
self:NetworkWeapon()
TacRP:PlayerSendAttInv(self:GetOwner())
self:InvalidateCache()
self:SetBaseSettings()
if self:GetValue("TryUnholster") then
self:DoDeployAnimation()
end
self:RestoreClip(self.Primary.ClipSize)
end

View File

@@ -0,0 +1,211 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = false
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Складной нож"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.NoAimAssist = true
SWEP.SubCatTier = "9Special"
SWEP.SubCatType = "8Melee Weapon"
SWEP.ViewModel = "models/weapons/tacint/v_knife.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_knife.mdl"
SWEP.NoRanger = true
SWEP.NoStatBox = false
SWEP.Slot = 0
SWEP.NPCUsable = false
SWEP.PrimaryMelee = true
SWEP.MeleeDamage = 35
SWEP.MeleeAttackTime = 0.4
SWEP.MeleeRange = 72
SWEP.MeleeAttackMissTime = 0.5
SWEP.MeleeDelay = 0.15
SWEP.MeleeThrowForce = 2000
SWEP.MeleeDamageType = DMG_SLASH
SWEP.MeleeRechargeRate = 1
SWEP.MeleePerkStr = 0.5
SWEP.MeleePerkAgi = 0.5
SWEP.MeleePerkInt = 0.5
SWEP.Lifesteal = 0
SWEP.DamageCharge = 0
SWEP.Firemode = 0
SWEP.RPM = 120
SWEP.CanBlindFire = false
SWEP.Ammo = ""
SWEP.ClipSize = -1
SWEP.Primary.ClipSize = -1
// handling
SWEP.MoveSpeedMult = 1
SWEP.MeleeSpeedMult = 1
SWEP.MeleeSpeedMultTime = 0.5
SWEP.SprintToFireTime = 0.25
SWEP.QuickNadeTimeMult = 0.8
SWEP.Scope = false
SWEP.Sway = 0
// hold types
SWEP.HoldType = "knife"
SWEP.HoldTypeSprint = "knife"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_PISTOL
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_PISTOL
SWEP.GestureBash = ACT_HL2MP_GESTURE_RANGE_ATTACK_KNIFE
SWEP.GestureBash2 = ACT_HL2MP_GESTURE_RANGE_ATTACK_MELEE
SWEP.MidAirSpreadPenalty = 0
SWEP.PassiveAng = Angle(-2.5, 0, 0)
SWEP.PassivePos = Vector(1, 0, -5)
SWEP.SprintAng = Angle(0, 0, 0)
SWEP.SprintPos = Vector(2, 0, -5)
SWEP.CustomizeAng = Angle(0, 25, 0)
SWEP.CustomizePos = Vector(2, 0, -12)
SWEP.SprintMidPoint = {
Pos = Vector(2, 0, -5),
Ang = Angle(0, 0, 0)
}
SWEP.Sound_Lunge = "npc/fast_zombie/leap1.wav"
SWEP.HolsterVisible = false
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_GEAR
SWEP.HolsterPos = Vector(2, 0, 0)
SWEP.HolsterAng = Angle(-90, -90, 15)
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Technique",
Category = "melee_tech",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[2] = {
PrintName = "Special",
Category = "melee_spec",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[3] = {
PrintName = "Boost",
Category = "melee_boost",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
}
SWEP.FreeAim = false
SWEP.DrawCrosshair = true
SWEP.DrawCrosshairInSprint = true
SWEP.CrosshairStatic = true
function SWEP:PrimaryAttack()
local stop = self:RunHook("Hook_PreShoot")
if stop then return end
local owner = self:GetOwner()
if IsValid(owner) then
local tr = owner:GetEyeTrace(72)
if IsValid(tr.Entity) and tr.Entity.LVS then return end
end
self:Melee()
return
end
function SWEP:ThinkSprint()
end
function SWEP:ThinkSights()
end
function SWEP:ThinkHoldBreath()
local ret = self:RunHook("Hook_Recharge")
if ret then return end
local f = 10 - math.min(self:GetValue("MeleePerkInt"), 0.5) * 2 - math.max((self:GetValue("MeleePerkInt") - 0.5) * 2, 0) * 6
self:SetBreath(math.min(1, self:GetBreath() + FrameTime() / f * self:GetValue("MeleeRechargeRate")))
end
SWEP.NoBreathBar = false
SWEP.BreathSegmentSize = 0
local breath_a = 0
local last = 1
local lastt = 0
function SWEP:DrawBreathBar(x, y, w, h)
if self:GetValue("NoBreathBar") then return end
local seg = self:GetValue("BreathSegmentSize")
if CurTime() > lastt + 1 then
breath_a = math.Approach(breath_a, 0, FrameTime() * 2)
elseif breath_a < 1 then
breath_a = math.Approach(breath_a, 1, FrameTime())
end
local breath = self:GetBreath()
if last != self:GetBreath() then
lastt = CurTime()
last = breath
end
if breath_a == 0 then return end
x = x - w / 2
y = y - h / 2
surface.SetDrawColor(90, 90, 90, 200 * breath_a)
surface.DrawOutlinedRect(x - 1, y - 1, w + 2, h + 2, 1)
surface.SetDrawColor(0, 0, 0, 75 * breath_a)
surface.DrawRect(x, y, w, h)
if seg > 0 then
local segcount = math.ceil(1 / seg)
surface.SetDrawColor(255, 255, 255, 200 * breath_a)
for i = 1, segcount - 1 do
local d = i / segcount
surface.DrawLine(x + w * d, y, x + w * d, y + h)
end
end
if seg > 0 and breath < seg then
surface.SetDrawColor(255, 128, 0, 150 * breath_a)
else
surface.SetDrawColor(255, 255, 255, 150 * breath_a)
end
surface.DrawRect(x, y, w * breath, h)
end
function SWEP:CalcView(ply, pos, ang, fov)
return pos, ang, fov
end
SWEP.AutoSpawnable = false

View File

@@ -0,0 +1,183 @@
AddCSLuaFile()
SWEP.Base = "tacrp_base"
// spawnable
SWEP.Spawnable = false
SWEP.AdminOnly = false
SWEP.NoAimAssist = true
// names and stuff
SWEP.PrintName = "Arctic's Tactical RP Base Grenade"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "9Special"
SWEP.SubCatType = "9Throwable"
SWEP.Description = ""
SWEP.ViewModel = "models/weapons/cstrike/c_eq_fraggrenade.mdl"
SWEP.WorldModel = "models/weapons/w_eq_fraggrenade.mdl"
SWEP.ViewModelFOV = 65
SWEP.NoRanger = true
SWEP.NoStatBox = true
SWEP.NPCUsable = false
SWEP.Slot = 4
SWEP.FreeAim = false
SWEP.DrawCrosshair = true
SWEP.DrawCrosshairInSprint = true
SWEP.CrosshairStatic = true
SWEP.Scope = false
SWEP.CanBlindFire = false
SWEP.CanQuickNade = false
SWEP.CanMeleeAttack = false
SWEP.Firemode = 0
SWEP.Ammo = ""
SWEP.PrimaryGrenade = ""
SWEP.Sway = 0
SWEP.QuickNadeTimeMult = 0.6
function SWEP:Equip(newowner)
local wep = self:GetOwner():GetActiveWeapon()
if self:GetOwner():IsPlayer() and wep != self and wep.ArcticTacRP and !wep:CheckGrenade(nil, true) then
self:GetOwner():SetNWInt("ti_nade", TacRP.QuickNades[self.PrimaryGrenade].Index)
end
if engine.ActiveGamemode() == "terrortown" and SERVER then
if self:IsOnFire() then
self:Extinguish()
end
self.fingerprints = self.fingerprints or {}
if !table.HasValue(self.fingerprints, newowner) then
table.insert(self.fingerprints, newowner)
end
if self:HasSpawnFlags(SF_WEAPON_START_CONSTRAINED) then
local flags = self:GetSpawnFlags()
local newflags = bit.band(flags, bit.bnot(SF_WEAPON_START_CONSTRAINED))
self:SetKeyValue("spawnflags", newflags)
end
end
if engine.ActiveGamemode() == "terrortown" and SERVER and IsValid(newowner) and (self.StoredAmmo or 0) > 0 and self.Primary.Ammo != "none" then
newowner:GiveAmmo(self.StoredAmmo, self.Primary.Ammo)
self.StoredAmmo = 0
end
end
function SWEP:ThinkSprint()
end
function SWEP:ThinkSights()
end
function SWEP:ThinkGrenade()
if self:GetPrimedGrenade() and self:GetAnimLockTime() < CurTime() then
if !self:GetOwner():KeyDown(self.GrenadeDownKey) then
self:ThrowGrenade()
self:SetPrimedGrenade(false)
elseif SERVER and self.GrenadeDownKey == IN_ATTACK then
self.GrenadeThrowCharge = math.Clamp(CurTime() - self:GetAnimLockTime(), 0, 0.25) * 2
end
elseif !self:GetPrimedGrenade() then
local nade = TacRP.QuickNades[self:GetValue("PrimaryGrenade")]
if !TacRP.IsGrenadeInfiniteAmmo(nade) and self:GetOwner():GetAmmoCount(nade.Ammo) == 0 then
if SERVER then
self:Remove()
elseif CLIENT and IsValid(self:GetOwner():GetPreviousWeapon()) and self:GetOwner():GetPreviousWeapon():IsWeapon() then
input.SelectWeapon(self:GetOwner():GetPreviousWeapon())
end
end
end
end
function SWEP:PrimaryAttack()
if engine.ActiveGamemode() == "terrortown" and GetRoundState() == ROUND_PREP and
((TTT2 and !GetConVar("ttt_nade_throw_during_prep"):GetBool()) or (!TTT2 and GetConVar("ttt_no_nade_throw_during_prep"):GetBool())) then
return
end
self.Primary.Automatic = false
self.Secondary.Automatic = false
self.GrenadeDownKey = IN_ATTACK
self.GrenadeThrowOverride = false
self.GrenadeThrowCharge = 0
if self:GetValue("Melee") and self:GetOwner():KeyDown(IN_USE) then
self:Melee()
return
end
if self:StillWaiting() then
return
end
self:SetBaseSettings()
local stop = self:RunHook("Hook_PreShoot")
if stop then return end
self:PrimeGrenade()
self:SetNextPrimaryFire(self:GetAnimLockTime())
self:SetNextSecondaryFire(self:GetAnimLockTime())
self:RunHook("Hook_PostShoot")
if game.SinglePlayer() and SERVER then self:CallOnClient("PrimaryAttack") end
end
function SWEP:SecondaryAttack()
if engine.ActiveGamemode() == "terrortown" and GetRoundState() == ROUND_PREP and GetConVar("ttt_no_nade_throw_during_prep"):GetBool() then
return
end
self.Primary.Automatic = false
self.Secondary.Automatic = false
self.GrenadeDownKey = IN_ATTACK2
self.GrenadeThrowOverride = true
if self:StillWaiting() then
return
end
self:SetBaseSettings()
local stop = self:RunHook("Hook_PreShoot")
if stop then return end
self:PrimeGrenade()
self:SetNextPrimaryFire(self:GetAnimLockTime())
self:SetNextSecondaryFire(self:GetAnimLockTime())
self:RunHook("Hook_PostShoot")
if game.SinglePlayer() and SERVER then self:CallOnClient("SecondaryAttack") end
end
function SWEP:Reload()
end
function SWEP:PreDrop()
if SERVER and IsValid(self:GetOwner()) and self.Primary.Ammo != "" and self.Primary.Ammo != "none" then
local ammo = self:Ammo1()
if ammo > 0 then
self.StoredAmmo = 1
self:GetOwner():RemoveAmmo(1, self.Primary.Ammo)
end
end
end

View File

@@ -0,0 +1,327 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Molot Bekas-16M"
SWEP.AbbrevName = "Bekas-16M"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "4Consumer"
SWEP.SubCatType = "5Shotgun"
SWEP.Description = "Accurate hunting shotgun with low damage."
SWEP.Description_Quote = "\"If you can hear them but can't shoot them, you can probably grenade them.\"" --Hardcore Henry (2016) (It's not a Bekas in that exact scene, but one is used later on in the complex so uuuuhhhhh explode)
SWEP.Trivia_Caliber = "16 Gauge"
SWEP.Trivia_Manufacturer = "Molot"
SWEP.Trivia_Year = "1999"
SWEP.Faction = TacRP.FACTION_MILITIA
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_bekas.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_bekas.mdl"
SWEP.Slot = 2
SWEP.SlotAlt = 3
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 24,
Damage_Min = 10,
Range_Min = 1200,
ClipSize = 6,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 14,
Damage_Min = 6,
Range_Min = 400,
Range_Max = 2500,
Num = 6,
ClipSize = 6,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 8,
Damage_Min = 4,
Range_Min = 500,
Range_Max = 2500,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 1.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.75,
[HITGROUP_RIGHTARM] = 0.75,
[HITGROUP_LEFTLEG] = 0.5,
[HITGROUP_RIGHTLEG] = 0.5,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilDissipationRate = 5,
RecoilMaximum = 12,
RecoilSpreadPenalty = 0.01,
HipFireSpreadPenalty = 0.015,
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.Shotgun
// "ballistics"
SWEP.Damage_Max = 18
SWEP.Damage_Min = 5
SWEP.Range_Min = 200 // distance for which to maintain maximum damage
SWEP.Range_Max = 2000 // distance at which we drop to minimum damage
SWEP.Penetration = 1 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.47
SWEP.ArmorBonus = 0.25
SWEP.Num = 6
SWEP.MuzzleVelocity = 11000
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
// misc. shooting
SWEP.Firemode = 1
SWEP.FiremodeName = "Pump-Action" // only used externally for firemode name distinction
SWEP.RPM = 60
SWEP.ShootTimeMult = 0.85
SWEP.Spread = 0.015
SWEP.ShotgunPelletSpread = 0.0075
SWEP.HipFireSpreadPenalty = 0.025
SWEP.MidAirSpreadPenalty = 0
SWEP.ScopedSpreadPenalty = 0
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 3
SWEP.RecoilResetTime = 0.25 // time after you stop shooting for recoil to start dissipating
SWEP.RecoilDissipationRate = 1
SWEP.RecoilFirstShotMult = 1.1
SWEP.RecoilVisualKick = 2
SWEP.RecoilKick = 15
SWEP.RecoilStability = 0.4
SWEP.RecoilSpreadPenalty = 0.02
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.9
SWEP.ShootingSpeedMult = 0.7
SWEP.SightedSpeedMult = 0.7
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.36
SWEP.SprintToFireTime = 0.4
SWEP.Sway = 1
SWEP.ScopedSway = 0.2
SWEP.FreeAimMaxAngle = 5
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.HoldTypeNPC = "shotgun"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_SHOTGUN
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SHOTGUN
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -4)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(4, -2, -4)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(-0.57, -0.6, 2)
SWEP.SightPos = Vector(-3.45, -5, -2.7)
SWEP.CorrectivePos = Vector(0.275, 0, -0.2)
SWEP.CorrectiveAng = Angle(1.21, 0.1, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK2
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 5
SWEP.DefaultAmmo = 0
SWEP.Ammo = "buckshot"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ShotgunReload = true
SWEP.ReloadTimeMult = 1
// sounds
local path = "TacRP/weapons/bekas/"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Sound_Shoot_Silenced = "TacRP/weapons/sg551/sg551_fire_silenced-1.wav"
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 0 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_shotgun"
SWEP.EjectEffect = 3
SWEP.EjectDelay = 0.5
// anims
SWEP.AnimationTranslationTable = {
["fire"] = {"shoot1", "shoot2"},
["blind_fire"] = {"blind_shoot1"},
["melee"] = {"melee1", "melee2"},
["reload"] = {"reload", "reload2"},
["jam"] = "reload_finish"
}
// attachments
SWEP.AttachmentElements = {
["optic"] = {
BGs_VM = {
{5, 1}
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium"},
Bone = "ValveBiped.bekas_rootbone",
WMBone = "ValveBiped.Bip01_R_Hand",
InstalledElements = {"optic"},
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
VMScale = 0.75,
Pos_VM = Vector(-3.2, 0, 8),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(11, 0.85, -7),
Ang_WM = Angle(-25, 3.5, 180),
},
[2] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom"},
Bone = "ValveBiped.bekas_rootbone",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
VMScale = 1.25,
Pos_VM = Vector(-1, -0.3, 24),
Ang_VM = Angle(90, 0, -90),
Pos_WM = Vector(25, 0, -12),
Ang_WM = Angle(-25, 3.5, 90),
},
[3] = {
PrintName = "Accessory",
Category = {"acc", "acc_sling", "acc_duffle", "acc_extmag_shotgun_tube"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[4] = {
PrintName = "Bolt",
Category = {"bolt_manual"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Trigger",
Category = {"trigger_manual", "trigger_pump2"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Ammo",
Category = {"ammo_shotgun"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("TacInt_Bekas.Insertshell", path .. "insertshell-1.wav")
addsound("TacInt_Bekas.Movement", path .. "movement-1.wav")
addsound("TacInt_Bekas.PumpBack", path .. "pump_backward-1.wav")
addsound("TacInt_Bekas.PumpForward", path .. "pump_forward-1.wav")

View File

@@ -0,0 +1,174 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "C4 Detonator"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.NoAimAssist = true
SWEP.SubCatTier = "9Special"
SWEP.SubCatType = "9Equipment"
SWEP.Description = "Device for touching off C4 charges or other types of remote explosives."
SWEP.Description_Quote = "\"Yeah, fuck you too!\"" -- The Thing (1982)
SWEP.ViewModel = "models/weapons/tacint/v_c4.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_c4_det.mdl"
SWEP.NoRanger = true
SWEP.NoStatBox = true
SWEP.ArcadeStats = {
MeleeSpeedMult = 1,
}
SWEP.Slot = 4
SWEP.NPCUsable = false
// misc. shooting
SWEP.Firemode = 1
SWEP.RPM = 120
SWEP.CanBlindFire = false
SWEP.Ammo = "ti_c4"
SWEP.ClipSize = -1
SWEP.Primary.ClipSize = -1
SWEP.SupplyAmmoAmount = 3
// handling
SWEP.MoveSpeedMult = 1
SWEP.MeleeSpeedMultTime = 2 // seconds to apply slow down for
SWEP.SprintToFireTime = 0.25
SWEP.Scope = false
SWEP.NoSecondaryMelee = true
// hold types
SWEP.HoldType = "normal"
SWEP.HoldTypeSprint = "normal"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_PISTOL
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_PISTOL
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(1, -2, -5)
SWEP.SprintAng = Angle(0, 30, 0)
SWEP.SprintPos = Vector(2, 0, -12)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_GEAR
SWEP.HolsterPos = Vector(2, 0, 0)
SWEP.HolsterAng = Angle(-90, -90, 15)
// sounds
local path = "TacRP/weapons/c4/"
SWEP.AnimationTranslationTable = {
["deploy"] = "deploy",
["melee"] = {"melee1", "melee2"}
}
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Accessory",
Category = {"acc_holster"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[2] = {
PrintName = "Perk",
Category = {"perk_melee", "perk_throw"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
}
}
SWEP.FreeAim = false
SWEP.AttachmentCapacity = 30 // amount of "Capacity" this gun can accept
SWEP.DrawCrosshair = false
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("TacInt_C4_Detonator.Detonator_Press", path .. "detonator_press.wav")
addsound("TacInt_C4_Detonator.antenna_open", path .. "antenna_open.wav")
function SWEP:PrimaryAttack()
if self:GetValue("Melee") then
if self:GetOwner():KeyDown(IN_USE) then
self.Primary.Automatic = true
self:Melee()
return
end
end
if self:StillWaiting() then return end
self:SetBaseSettings()
self:PlayAnimation("detonate")
for i, k in pairs(ents.FindByClass("tacrp_proj_nade_*")) do
if (k:GetOwner() == self:GetOwner() or k.Attacker == self:GetOwner()) and k.RemoteFuse then
k:RemoteDetonate()
end
end
self:SetNextPrimaryFire(CurTime() + (60 / self:GetValue("RPM")))
end
function SWEP:IsQuickNadeAllowed()
return true // Otherwise it's useless!
end
function SWEP:SecondaryAttack()
local nade = self:GetOwner():GetNWInt("ti_nade")
if nade != 12 and nade != 6 then
self:GetOwner():SetNWInt("ti_nade", 12)
end
self:PrimeGrenade()
end
SWEP.AutoSpawnable = false
if engine.ActiveGamemode() == "terrortown" then
SWEP.AutoSpawnable = false
SWEP.HolsterVisible = false
SWEP.Kind = WEAPON_EQUIP
SWEP.Slot = 6
SWEP.CanBuy = { ROLE_TRAITOR }
SWEP.EquipMenuData = {
type = "Weapon",
desc = "A remote detonator for C4s and Breaching Charges.\nComes with 1 C4 and 3 Breaching Charges.",
}
function SWEP:TTTBought(buyer)
buyer:GiveAmmo(1, "ti_c4")
buyer:GiveAmmo(3, "ti_charge")
end
end

View File

@@ -0,0 +1,116 @@
SWEP.Base = "tacrp_m320"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "HK M320LE"
SWEP.AbbrevName = "M320LE"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.NoAimAssist = true
SWEP.SubCatTier = "9Special"
SWEP.SubCatType = "6Launcher"
SWEP.Description = "Law Enforcement version of the M320 sanctioned for less-lethal munitions. Fires beanbag rounds that incapacitate on direct hit."
SWEP.Description_Quote = "That is one dangerous beanbag..."
SWEP.Trivia_Caliber = "40mm Grenades"
SWEP.Trivia_Manufacturer = "Heckler & Koch"
SWEP.Trivia_Year = "2008"
SWEP.Faction = TacRP.FACTION_NEUTRAL
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_m320.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_m320_civ.mdl"
SWEP.DefaultSkin = 1
SWEP.NoRanger = true
SWEP.Slot = 4
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
},
}
// "ballistics"
SWEP.Damage_Max = 100
SWEP.Damage_Min = 100
SWEP.Range_Max = 2000
SWEP.Range_Min = 800
SWEP.ShootEnt = "tacrp_proj_40mm_beanbag"
SWEP.ShootEntForce = 7000
SWEP.Spread = 0.01
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 1,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 7000
SWEP.Num = 1
// sounds
local path = "TacRP/weapons/m320/"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Vol_Shoot = 100
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// anims
SWEP.Attachments = {
[1] = {
PrintName = "Ammo",
Category = "ammo_40mm_civ",
AttachSound = "TacRP/weapons/m320/shell_in-1.wav",
DetachSound = "TacRP/weapons/m320/shell_out-1.wav",
},
[2] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock2", "acc_holster"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[3] = {
PrintName = "Perk",
Category = {"perk", "perk_shooting", "perk_reload", "perk_melee"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("TacInt_m320.Tube_Open", path .. "tube_open-1.wav")
addsound("TacInt_m320.Tube_close", path .. "tube_close-1.wav")
addsound("TacInt_m320.shell_out", path .. "shell_out-1.wav")
addsound("TacInt_m320.shell_in", path .. "shell_in-1.wav")
addsound("TacInt_m320.buttstock_back", path .. "buttstock_back-1.wav")
addsound("TacInt_m320.sight_flipup", path .. "sight_flipup-1.wav")
SWEP.AutoSpawnable = false

View File

@@ -0,0 +1,358 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Glock 17"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "4Consumer"
SWEP.SubCatType = "1Pistol"
SWEP.Description = "Polymer pistol with larger-than-standard capacity and a fast fire rate."
SWEP.Description_Quote = "Does not show up on airport metal detectors."
SWEP.Trivia_Caliber = "9x19mm"
SWEP.Trivia_Manufacturer = "Glock Ges.m.b.H"
SWEP.Trivia_Year = "1982"
SWEP.Faction = TacRP.FACTION_NEUTRAL
SWEP.Credits = "Assets: Twinke Masta \nSounds: Vunsunta \nAnimations: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint_extras/v_glock_new.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_glock_new.mdl"
SWEP.Slot = 1
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 24,
Damage_Min = 12,
RecoilKick = 3,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 13,
Damage_Min = 5,
Range_Min = 500,
Range_Max = 1750,
RPM = 600,
RPMMultSemi = 1,
RecoilMaximum = 10,
RecoilDissipationRate = 10,
RecoilSpreadPenalty = 0.0045,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 7,
Damage_Min = 3,
HipFireSpreadPenalty = 0.012,
RecoilSpreadPenalty = 0.002,
},
[TacRP.BALANCE_OLDSCHOOL] = {
Description = "Lightweight polymer handgun with a high fire rate but below-average spread.",
HipFireSpreadPenalty = 0.01,
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.Pistol
// "ballistics"
SWEP.Damage_Max = 18
SWEP.Damage_Min = 10
SWEP.Range_Min = 500 // distance for which to maintain maximum damage
SWEP.Range_Max = 1800 // distance at which we drop to minimum damage
SWEP.Penetration = 3 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.45
SWEP.ArmorBonus = 0.5
SWEP.MuzzleVelocity = 11000
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
}
// misc. shooting
SWEP.Firemode = 1
SWEP.RPM = 550
SWEP.RPMMultSemi = 0.65
SWEP.Spread = 0.008
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 4
SWEP.RecoilResetTime = 0.035
SWEP.RecoilDissipationRate = 16
SWEP.RecoilFirstShotMult = 1 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 1.25
SWEP.RecoilKick = 4
SWEP.RecoilStability = 0.25
SWEP.RecoilSpreadPenalty = 0.005
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.975
SWEP.ShootingSpeedMult = 0.9
SWEP.SightedSpeedMult = 0.8
SWEP.ReloadSpeedMult = 0.75
SWEP.AimDownSightsTime = 0.25
SWEP.SprintToFireTime = 0.25
SWEP.Sway = 1
SWEP.ScopedSway = 0.5
SWEP.FreeAimMaxAngle = 2.5
// hold types
SWEP.HoldType = "revolver"
SWEP.HoldTypeSprint = "normal"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_PISTOL
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_PISTOL
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(0, -2, -5)
SWEP.BlindFireSuicideAng = Angle(-125, 0, 45)
SWEP.BlindFireSuicidePos = Vector(25, 12, -5)
SWEP.SprintAng = Angle(0, 30, 0)
SWEP.SprintPos = Vector(2, 0, -12)
SWEP.SightAng = Angle(-0.01, 0.35, 0)
SWEP.SightPos = Vector(-3.3, 0, -3.35)
SWEP.CorrectivePos = Vector(0.02, -1, 0)
SWEP.CorrectiveAng = Angle(0.05, -0.05, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_PISTOL
SWEP.HolsterPos = Vector(0, 3, -4)
SWEP.HolsterAng = Angle(90, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 18
SWEP.DefaultAmmo = 0
SWEP.Ammo = "pistol1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadUpInTime = 0.85
SWEP.DropMagazineTime = 0.2
SWEP.ReloadTimeMult = 1.4
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/glock_new.mdl"
SWEP.DropMagazineImpact = "pistol"
// sounds
local path = "tacrp/weapons/p2000/p2000_"
local path2 = "tacrp_extras/glock/"
SWEP.Sound_Shoot = "^" .. path2 .. "fire-1new.wav"
SWEP.Sound_Shoot_Silenced = path2 .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 110
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
SWEP.MuzzleEffect = "muzzleflash_pistol"
SWEP.EjectEffect = 1
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "draw",
["fire_iron"] = "shoot2",
["fire"] = {"shoot1", "shoot2", "shoot3"},
["blind_fire"] = {"blind_shoot1", "blind_shoot2", "blind_shoot3"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.5, -0.6),
vm_ang = Angle(0, 2, 0),
t = 0.2,
tmax = 0.2,
bones = {
{
bone = "ValveBiped.slide",
pos = Vector(0, 0, -3),
t0 = 0,
t1 = 0.1,
},
{
bone = "ValveBiped.hammer",
ang = Angle(-15, 0, 0),
t0 = 0,
t1 = 0.15,
},
{
bone = "ValveBiped.Bip01_R_Finger1",
ang = Angle(0, -15, 0),
t0 = 0,
t1 = 0.15,
},
{
bone = "ValveBiped.Bip01_R_Finger11",
ang = Angle(-35, 0, 0),
t0 = 0,
t1 = 0.1,
},
},
}
SWEP.NoIdle = true --fixes animation bug, why was this set to false??
SWEP.ShootTimeMult = 0.45
SWEP.LastShot = true
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = "optic_pistol",
Bone = "ValveBiped.slide",
WMBone = "Box01",
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 1,
WMScale = 1.4,
Pos_VM = Vector(0.21, 0, -0.15),
Ang_VM = Angle(0, 90, 180),
Pos_WM = Vector(0, -3, -1),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.barrel_assembly",
WMBone = "Box01",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
VMScale = 0.6,
WMScale = 0.6,
Pos_VM = Vector(-0.5, 0.25, 7.25),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0.05, 8.9, -1.7),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.p2000_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
VMScale = 1,
WMScale = 1.3,
Pos_VM = Vector(-2.1, -0.21, 6.5),
Ang_VM = Angle(90, 0, 180),
Pos_WM = Vector(0.1, 5, -2.75),
Ang_WM = Angle(0, -90, 180),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_extmag_smg", "acc_holster", "acc_brace"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_semi"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_pistol"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_extras_glock.clip_in", path .. "clip_in.wav")
addsound("tacint_extras_glock.clip_in-mid", path .. "clip_in-mid.wav")
addsound("tacint_extras_glock.clip_out", path2 .. "magout.mp3")
addsound("tacint_extras_glock.slide_action", path .. "slide_action.wav")
addsound("tacint_extras_glock.slide_shut", path .. "slide_shut.wav")
addsound("tacint_extras_glock.cock_hammer", path .. "cockhammer.wav")

View File

@@ -0,0 +1,397 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "PGM Hécate II"
SWEP.AbbrevName = "Hécate II"
SWEP.Category = "[FT] Оружие" // "Tactical RP (Extras)"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "7Sniper Rifle"
SWEP.Description = "Heavy anti-materiel rifle that can kill in one shot. Too heavy to bash with. \nEquipped with a 12x scope by default."
SWEP.Description_Quote = "Gun Runner tested, NCR approved."
SWEP.Trivia_Caliber = ".50 BMG"
SWEP.Trivia_Manufacturer = "PGM Précision"
SWEP.Trivia_Year = "1993"
SWEP.Faction = TacRP.FACTION_MILITIA
SWEP.Credits = "Assets: Toby Burnside\nSource: Fallout 4: New Vegas Project"
SWEP.ViewModel = "models/weapons/tacint_extras/v_hecate.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_hecate.mdl"
SWEP.Slot = 2
SWEP.SlotAlt = 3
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 80,
Damage_Min = 150,
Range_Min = 700,
Range_Max = 5000,
},
[TacRP.BALANCE_TTT] = { // this is a buyable weapon in TTT
Damage_Max = 80,
Damage_Min = 200,
Range_Min = 500,
Range_Max = 5000,
Penetration = 75,
RecoilDissipationRate = 0.5,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.75,
[HITGROUP_RIGHTARM] = 0.75,
[HITGROUP_LEFTLEG] = 0.5,
[HITGROUP_RIGHTLEG] = 0.5,
[HITGROUP_GEAR] = 0.5
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 90,
Damage_Min = 75,
Range_Min = 4000,
Range_Max = 8000,
},
[TacRP.BALANCE_OLDSCHOOL] = {
HipFireSpreadPenalty = 0.025,
}
}
// "ballistics"
SWEP.Damage_Max = 175 // damage at minimum range
SWEP.Damage_Min = 130 // damage at maximum range
SWEP.Range_Min = 1500 // distance for which to maintain maximum damage
SWEP.Range_Max = 9000 // distance at which we drop to minimum damage
SWEP.Penetration = 40 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 1.5
SWEP.ArmorBonus = 5
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5, // nobody is surviving this
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.75,
[HITGROUP_RIGHTARM] = 0.75,
[HITGROUP_LEFTLEG] = 0.5,
[HITGROUP_RIGHTLEG] = 0.5,
[HITGROUP_GEAR] = 0.5
}
SWEP.MuzzleVelocity = 20000
SWEP.ShootTimeMult = 1.35
// misc. shooting
SWEP.Firemode = 1
SWEP.FiremodeName = "Bolt-Action" // only used externally for firemode name distinction
SWEP.RPM = 25
SWEP.Spread = 0
SWEP.HipFireSpreadPenalty = 0.06
SWEP.PeekPenaltyFraction = 0.2
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 1
SWEP.RecoilResetTime = 0.25
SWEP.RecoilDissipationRate = 1.25
SWEP.RecoilFirstShotMult = 1
SWEP.RecoilMultCrouch = 1
SWEP.RecoilVisualKick = 5
SWEP.RecoilKick = 10
SWEP.RecoilStability = 0.75
SWEP.RecoilSpreadPenalty = 0.05
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.875
SWEP.ShootingSpeedMult = 0.4
SWEP.SightedSpeedMult = 0.5
SWEP.ReloadSpeedMult = 0.3
SWEP.AimDownSightsTime = 0.7
SWEP.SprintToFireTime = 0.7
SWEP.Sway = 2.5
SWEP.ScopedSway = 0.2
SWEP.FreeAimMaxAngle = 9
SWEP.Bipod = true
SWEP.BipodRecoil = 1
SWEP.BipodKick = 0.15
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_CROSSBOW
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(2, -2, -6)
SWEP.BlindFireAng = Angle(0, 15, -60)
SWEP.BlindFirePos = Vector(1, -2, -1)
SWEP.BlindFireLeftAng = Angle(75, 0, 0)
SWEP.BlindFireLeftPos = Vector(8, 10, -6)
SWEP.BlindFireRightAng = Angle(-75, 0, 0)
SWEP.BlindFireRightPos = Vector(-8, 12, -4)
SWEP.BlindFireSuicideAng = Angle(0, 135, 0)
SWEP.BlindFireSuicidePos = Vector(-4, 44, -35)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -4)
SWEP.SightAng = Angle(0.02, 0.11, 0)
SWEP.SightPos = Vector(-3.835, -7.5, -4.07)
SWEP.CorrectivePos = Vector(0.025, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK2
SWEP.HolsterPos = Vector(5, 6, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// scope
SWEP.Scope = true
SWEP.ScopeOverlay = Material("tacrp/scopes/sniper.png", "mips smooth") // Material("path/to/overlay")
SWEP.ScopeFOV = 90 / 12
SWEP.ScopeLevels = 1 // 2 = like CS:S
SWEP.ScopeHideWeapon = true
SWEP.ScopeOverlaySize = 0.75
SWEP.CanMeleeAttack = false
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 7
SWEP.DefaultAmmo = 0
SWEP.Ammo = "357"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.AmmoTTT = "ti_sniper"
SWEP.Ammo_Expanded = "ti_sniper"
SWEP.ReloadTimeMult = 1.4
SWEP.DropMagazineImpact = "metal"
SWEP.DropMagazineModel = "models/weapons/tacint/magazines/uratio.mdl"
SWEP.ReloadUpInTime = 1.75
SWEP.DropMagazineTime = 0.8
// sounds
local path = "tacrp_extras/hecate/ax308_"
SWEP.Sound_Shoot = "^tacrp_extras/hecate/ax308_fire_1.wav"
SWEP.Sound_Shoot_Silenced = "TacRP/weapons/ak47/ak47_fire_silenced-1.wav"
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 1 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_m82_tacrp"
SWEP.EjectEffect = 2
SWEP.EjectDelay = 1.15
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "unholster",
["fire"] = "shoot1",
["blind_idle"] = "idle",
["blind_fire"] = "shoot1",
["reload"] = "reload",
}
SWEP.BulletBodygroups = {
[1] = {4, 1},
}
// attachments
SWEP.AttachmentElements = {
["optic"] = {
BGs_VM = {
{1, 2}
},
BGs_WM = {
{1, 2}
},
},
["irons"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
},
SortOrder = 2,
},
["tactical"] = {
BGs_VM = {
{2, 1}
},
BGs_WM = {
{2, 1}
},
},
["bipod"] = {
BGs_VM = {
{3, 1}
},
BGs_WM = {
{3, 1}
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"ironsights_sniper", "optic_cqb", "optic_medium", "optic_sniper"},
WMBone = "Box01",
Bone = "ValveBiped.uratio_rootbone",
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
InstalledElements = {"optic"},
VMScale = 0.9,
Pos_VM = Vector(-5.75, 0, 5),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 5.5, 2.2),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "barrel",
WMBone = "Box01",
Bone = "ValveBiped.uratio_rootbone",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
Pos_VM = Vector(-4.1, 0, 30),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 35, 0.25),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
WMBone = "Box01",
Bone = "ValveBiped.uratio_rootbone",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
Pos_VM = Vector(-3.9, -1.5, 19.25),
Ang_VM = Angle(90, 0, 270),
Pos_WM = Vector(-1.75, 22.5, -0.05),
Ang_WM = Angle(0, -90, 90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_extmag_sniper", "acc_sling", "acc_duffle", "acc_bipod"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_manual"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_manual"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_amr"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_extras_hecate.Clip_Out", path .. "magout.wav")
addsound("tacint_extras_hecate.Clip_In", path .. "magin.wav")
addsound("tacint_extras_hecate.Bolt_Back", path .. "boltrelease.wav")
addsound("tacint_extras_hecate.bolt_forward", path .. "boltback.wav")
addsound("tacint_extras_hecate.Bolt_Up", path .. "boltup.wav")
addsound("tacint_extras_hecate.bolt_down", path .. "boltdown.wav")
if engine.ActiveGamemode() == "terrortown" then
SWEP.AutoSpawnable = false
SWEP.Kind = WEAPON_HEAVY
SWEP.CanBuy = { ROLE_TRAITOR, ROLE_DETECTIVE }
SWEP.EquipMenuData = {
type = "Weapon",
desc = "Heavy bolt-action anti-materiel rifle.\nComes with 10 rounds.\n\nBEWARE: May be visible while holstered!",
}
function SWEP:TTTBought(buyer)
buyer:GiveAmmo(3, "ti_sniper")
end
end

View File

@@ -0,0 +1,358 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Colt M4A1"
SWEP.AbbrevName = "M4A1"
SWEP.Category = "[FT] Оружие" // "Tactical RP (Extras)"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "4Assault Rifle"
SWEP.Description = "A true American classic boasting high fire rate and balanced performance."
SWEP.Description_Quote = "\"Burn 'em, Eldridge!\"" --The Hurt Locker (2008)
SWEP.Trivia_Caliber = "5.56x45mm"
SWEP.Trivia_Manufacturer = "Colt"
SWEP.Trivia_Year = "1987"
SWEP.Faction = TacRP.FACTION_NEUTRAL // This is older military kit so it's not uncommon to see some captured examples in the hands of bad guys.
SWEP.Credits = [[
Model/Texture: Twinke Masta, DMG
Sound: Teh Strelok
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_extras/v_m4a1.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_m4a1.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 14,
Damage_Min = 8,
Range_Min = 600,
Range_Max = 2000,
RPM = 750,
RecoilSpreadPenalty = 0.0022,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 9,
Damage_Min = 5,
Range_Min = 600,
Range_Max = 2800,
RPM = 800,
RecoilSpreadPenalty = 0.0017,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilMaximum = 15,
RecoilPerShot = 1,
RecoilDissipationRate = 10,
RecoilSpreadPenalty = 0.005,
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 22
SWEP.Damage_Min = 15
SWEP.Range_Min = 1000
SWEP.Range_Max = 2800
SWEP.Penetration = 7 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.7
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 25000
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 800
SWEP.Spread = 0.0069
SWEP.ShootTimeMult = 0.5
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 10
SWEP.RecoilResetTime = 0
SWEP.RecoilDissipationRate = 35
SWEP.RecoilFirstShotMult = 1
SWEP.RecoilVisualKick = 0.75
SWEP.RecoilKick = 4.5
SWEP.RecoilStability = 0.25
SWEP.RecoilSpreadPenalty = 0.002
SWEP.HipFireSpreadPenalty = 0.04
SWEP.PeekPenaltyFraction = 0.2
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.925
SWEP.ShootingSpeedMult = 0.8
SWEP.SightedSpeedMult = 0.65
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.36
SWEP.SprintToFireTime = 0.38 // multiplies how long it takes to recover from sprinting
SWEP.Sway = 1.25
SWEP.ScopedSway = 0.15
SWEP.FreeAimMaxAngle = 4.5
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -4, -6)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, -4, -3)
SWEP.SightAng = Angle(0.1, 0, 0)
SWEP.SightPos = Vector(-4.154, -7.5, -4.45)
SWEP.CorrectivePos = Vector(-0.05, 0, 0.05)
SWEP.CorrectiveAng = Angle(0.03, 0.45, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint/magazines/m4.mdl"
SWEP.DropMagazineImpact = "metal"
SWEP.ReloadUpInTime = 1.3
SWEP.DropMagazineTime = 0.4
// sounds
local path = "TacRP/weapons/m4/m4_"
local path2 = "tacrp_extras/m4a1/m4a1_"
SWEP.Sound_Shoot = "^" .. path2 .. "fire-1.wav"
SWEP.Sound_Shoot_Silenced = path2 .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 120
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["fire_iron"] = "dryfire",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -1.5, -0.05),
vm_ang = Angle(0, 0.1, 0),
t = 0.25,
tmax = 0.25,
}
// attachments
SWEP.AttachmentElements = {
["sights"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
},
},
["chmount"] = {
BGs_VM = {
{1, 0}
},
BGs_WM = {
{1, 0}
},
AttPosMods = {
[1] = {
Pos_VM = Vector(-7.7, -0.05, 4),
Pos_WM = Vector(0.4, 3, 3.5),
}
},
SortOrder = 2,
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb_verytall", "optic_medium", "optic_sniper", "optic_ar"},
InstalledElements = {"sights"},
Bone = "ValveBiped.m4_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
VMScale = 1,
Pos_VM = Vector(-5.6, -0.075, 4),
Pos_WM = Vector(0.4, 3, 1.15),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90 + 3.5, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.m4_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
VMScale = 0.9,
Pos_VM = Vector(-3.95, 0, 25.65),
Pos_WM = Vector(1.4, 26, -0.5),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90 + 3.5, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.m4_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
Pos_VM = Vector(-3.9, -1.2, 13.5),
Pos_WM = Vector(2, 13, -0.5),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(-90, -90 + 3.5, 0),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_sling", "acc_duffle", "perk_extendedmag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_extras_m4a1.Remove_Clip", path2 .. "clipout.mp3")
addsound("tacint_extras_m4a1.Insert_Clip", path2 .. "clipin.mp3")
addsound("tacint_extras_m4a1.Insert_Clip-mid", path .. "insert_clip-mid.wav")
addsound("tacint_extras_m4a1.bolt_action", path .. "bolt_action.wav")
addsound("tacint_extras_m4a1.bolt_slap", path .. "bolt_slap.wav")
addsound("tacint_extras_m4a1.throw_catch", path .. "throw_catch.wav")

View File

@@ -0,0 +1,253 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "FIM-92 Stinger"
SWEP.AbbrevName = "Stinger"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.NoAimAssist = true
SWEP.SubCatTier = "9Special"
SWEP.SubCatType = "6Launcher"
SWEP.Description = "Homing anti-air missile launcher. High blast damage but limited effect on armored targets.\nRequires a lock-on in order to fire."
SWEP.Description_Quote = "\"A cornered fox is more dangerous than a jackal!\""
SWEP.Trivia_Caliber = "Infrared Homing Missile"
SWEP.Trivia_Manufacturer = "Raytheon Missiles and Defense"
SWEP.Trivia_Year = "1967"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = "Assets: Modern Warfare 2\nAnimations: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_stinger.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_stinger.mdl"
SWEP.NoRanger = true
SWEP.Slot = 2
SWEP.SlotAlt = 4
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
},
}
// "ballistics"
SWEP.Damage_Max = 100 // just to fool the ratings
SWEP.Damage_Min = 100
SWEP.Range_Max = 30000
SWEP.Range_Min = 5000
SWEP.ShootEnt = "tacrp_proj_stinger"
SWEP.ShootEntForce = 2000
SWEP.Num = 1
// misc. shooting
SWEP.Firemode = 1
SWEP.FiremodeName = "Single-Shot" // only used externally for firemode name distinction
SWEP.RPM = 60
SWEP.Spread = 0.01
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 1
SWEP.RecoilResetTime = 0.2// time after you stop shooting for recoil to start dissipating
SWEP.RecoilDissipationRate = 1
SWEP.RecoilFirstShotMult = 1 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 5
SWEP.RecoilVisualShake = 0.2
SWEP.RecoilKick = 0
SWEP.RecoilSpreadPenalty = 0 // extra spread per one unit of recoil
SWEP.CanBlindFire = false
SWEP.CannotHipFire = true
// lockon
// SWEP.LockOnAngle = math.cos(math.rad(5))
SWEP.LockOnTrackAngle = 5
SWEP.LockOnRange = 40000
SWEP.LockOnTime = 1
SWEP.ProvideTargetData = true
SWEP.LockOnOutOfSights = false
SWEP.LockOnInSights = true
SWEP.ShootOffset = Vector(0, 0, 0)
SWEP.ShootOffsetAngle = Angle(0, 0, 0)
SWEP.RequireLockOn = true // Cannot shoot without a lock
// handling
SWEP.MoveSpeedMult = 0.8
SWEP.ShootingSpeedMult = 0.25
SWEP.SightedSpeedMult = 0.5
SWEP.ReloadSpeedMult = 0.2
SWEP.AimDownSightsTime = 0.6
SWEP.SprintToFireTime = 0.8 // multiplies how long it takes to recover from sprinting
SWEP.DeployTimeMult = 1.25
// hold types
SWEP.HoldType = "passive"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeSighted = "rpg"
SWEP.HoldTypeBlindFire = false
SWEP.HoldTypeNPC = "ar2"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_RPG
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_AR2
SWEP.PassiveAng = Angle(40, -15, 0)
SWEP.PassivePos = Vector(4, 0, -4)
SWEP.SprintMidPoint = {
Pos = Vector(0, 0, 0),
Ang = Angle(0, 0, 0)
}
SWEP.BlindFireAng = Angle(0, 0, 0)
SWEP.BlindFirePos = Vector(1, -3, 0)
SWEP.BlindFireLeftAng = Angle(75, 0, 0)
SWEP.BlindFireLeftPos = Vector(8, 10, -6)
SWEP.BlindFireSuicideAng = Angle(0, 125, 0)
SWEP.BlindFireSuicidePos = Vector(-2, 25, -24)
SWEP.SprintAng = Angle(40, -15, 0)
SWEP.SprintPos = Vector(4, 0, -4)
SWEP.SightAng = Angle(0, 0, 0)
SWEP.SightPos = Vector(-0.62, -10, -4.57)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_SPECIAL
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// sway
SWEP.Sway = 3
SWEP.ScopedSway = 0.25
SWEP.FreeAimMaxAngle = 5
// melee
SWEP.CanMeleeAttack = false
// reload
SWEP.ClipSize = 1
SWEP.Ammo = "rpg_round"
// sounds
local path = "TacRP/weapons/rpg7/"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Sound_StartLockOn = "tacrp/check1.wav"
SWEP.Sound_FinishLockOn = "tacrp/locked1.wav"
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_deagle"
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "unholster",
["blind_fire"] = "aimed_fire",
["blind_idle"] = "aimed_idle",
}
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Ammo",
Category = {"ammo_stinger"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[2] = {
PrintName = "Accessory",
Category = {"acc", "acc_duffle", "acc_sling"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[3] = {
PrintName = "Perk",
Category = {"perk", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("TacInt_rpg7.jingle", path .. "handling-1.wav")
addsound("TacInt_rpg7.insert_rocket", path .. "insert_rocket.wav")
addsound("TacInt_rpg7.flipup_sight", path .. "flipup_sight.wav")
if engine.ActiveGamemode() == "terrortown" then
SWEP.AutoSpawnable = false
SWEP.Kind = WEAPON_EQUIP
SWEP.Slot = 6
SWEP.CanBuy = { ROLE_TRAITOR }
SWEP.LimitedStock = true
SWEP.EquipMenuData = {
type = "Weapon",
desc = "Rocket launcher. Can't explode at point blank.\nComes with 2 rockets.\n\nBEWARE: May be visible while holstered!",
}
function SWEP:TTTBought(buyer)
buyer:GiveAmmo(1, "RPG_Round")
end
end
function SWEP:ShouldAutoReload()
return !self:GetValue("NoAutoReload")
end
function SWEP:DoOldSchoolScopeBehavior()
return false
end

View File

@@ -0,0 +1,348 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "HK G36K"
SWEP.AbbrevName = "G36K"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "4Assault Rifle"
SWEP.Description = "Assault rifle with high muzzle velocity. Well suited for medium range sustained fire.\nEquipped with a 2x scope by default."
SWEP.Description_Quote = "\"Yeah, it was a good day.\"" -- Stargate SG-1 (S9E16)
SWEP.Trivia_Caliber = "5.56x45mm"
SWEP.Trivia_Manufacturer = "Heckler & Koch"
SWEP.Trivia_Year = "1996"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_g36k_hq.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_g36k.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 18,
Damage_Min = 13,
Range_Min = 1200,
Range_Max = 2800,
RPM = 550,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 9,
Damage_Min = 6,
RecoilKick = 1.5,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilSpreadPenalty = 0.003,
HipFireSpreadPenalty = 0.009
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 20
SWEP.Damage_Min = 16
SWEP.Range_Min = 1200 // distance for which to maintain maximum damage
SWEP.Range_Max = 3200 // distance at which we drop to minimum damage
SWEP.Penetration = 9 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.775
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.4,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 37000
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 750
SWEP.Spread = 0.0018
SWEP.ShootTimeMult = 0.5
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 10
SWEP.RecoilResetTime = 0
SWEP.RecoilDissipationRate = 40
SWEP.RecoilFirstShotMult = 1
SWEP.RecoilVisualKick = 0.8
SWEP.RecoilKick = 3
SWEP.RecoilStability = 0.5
SWEP.RecoilSpreadPenalty = 0.0015
SWEP.HipFireSpreadPenalty = 0.05
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.925
SWEP.ShootingSpeedMult = 0.85
SWEP.SightedSpeedMult = 0.6
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.4
SWEP.SprintToFireTime = 0.38
SWEP.Sway = 1.25
SWEP.ScopedSway = 0.15
SWEP.FreeAimMaxAngle = 4.25
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(40, -15, 0)
SWEP.SprintPos = Vector(5, 0, -4)
SWEP.SightAng = Angle(0, 0, 0)
SWEP.SightPos = Vector(-4.03, -2.5, -4.1)
SWEP.CorrectivePos = Vector(0, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// scope
SWEP.Scope = true
SWEP.ScopeOverlay = Material("tacrp/scopes/g36.png", "mips smooth") // Material("path/to/overlay")
SWEP.ScopeFOV = 90 / 2
SWEP.ScopeLevels = 1 // 2 = like CS:S
SWEP.ScopeHideWeapon = true
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint/magazines/g36k.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.4
SWEP.DropMagazineTime = 0.4
// sounds
local path = "TacRP/weapons/g36k/g36k_"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 120
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["fire_iron"] = "dryfire",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -1, -0.1),
vm_ang = Angle(0, 0.4, 0),
t = 0.25,
tmax = 0.25,
}
// attachments
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
}
},
["tactical"] = {
BGs_VM = {
{2, 1}
},
},
["irons"] = {
BGs_VM = {
{3, 1}
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"ironsights", "optic_cqb_nookp7", "optic_medium"},
Bone = "ValveBiped.g36k_rootbone",
WMBone = "Box01",
InstalledElements = {"irons"},
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
VMScale = 1,
Pos_VM = Vector(-6.4, 0.14, 7),
Pos_WM = Vector(0, 0, 2.75),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.g36k_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
Pos_VM = Vector(-3.45, 0.075, 24.5),
Pos_WM = Vector(-0.25, 24, -1),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.g36k_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
Pos_VM = Vector(-3.75, -0.75, 17),
Pos_WM = Vector(0.9, 15, -1),
Ang_VM = Angle(90, 0, -80),
Ang_WM = Angle(-70, -90, 0),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock", "acc_sling", "acc_duffle", "perk_extendedmag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("TacInt_g36k.remove_clip", path .. "remove_clip.wav")
addsound("TacInt_g36k.insert_clip", path .. "insert_clip.wav")
addsound("TacInt_g36k.bolt_action", path .. "bolt_action.wav")
addsound("TacInt_g36k.fire_select", path .. "fire_selector.wav")
addsound("TacInt_g36k.Buttstock_Back", path .. "buttstock_back.wav")

View File

@@ -0,0 +1,340 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "HK HK417"
SWEP.AbbrevName = "HK417"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "1Elite"
SWEP.SubCatType = "5Battle Rifle"
SWEP.Description = "Battle rifle with superb damage, fire rate and precision. Capable of automatic fire, although it is very unstable."
SWEP.Description_Quote = "\"Hey, he saved our asses back there, and right now he's all we got.\"" -- Spec Ops: The Line (2012)
SWEP.Trivia_Caliber = "7.62x51mm"
SWEP.Trivia_Manufacturer = "Heckler & Koch"
SWEP.Trivia_Year = "2006"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_hk417.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_hk417.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 38,
Damage_Min = 25,
ShootingSpeedMult = 0.5,
RecoilStability = 0.5,
},
[TacRP.BALANCE_TTT] = {
Description = "Battle rifle with high rate of fire.",
Damage_Max = 28,
Damage_Min = 20,
Range_Min = 600,
Range_Max = 2500,
RPM = 360,
RecoilResetInstant = true,
RecoilResetTime = 0.15,
RecoilDissipationRate = 12,
RecoilMaximum = 9,
RecoilSpreadPenalty = 0.01,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.75,
[HITGROUP_RIGHTARM] = 0.75,
[HITGROUP_LEFTLEG] = 0.5,
[HITGROUP_RIGHTLEG] = 0.5,
[HITGROUP_GEAR] = 0.5
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 18,
Damage_Min = 14,
RecoilDissipationRate = 10,
RecoilSpreadPenalty = 0.006,
},
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.BattleRifle
// "ballistics"
SWEP.Damage_Max = 42
SWEP.Damage_Min = 35
SWEP.Range_Min = 1200 // distance for which to maintain maximum damage
SWEP.Range_Max = 4200 // distance at which we drop to minimum damage
SWEP.Penetration = 12 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.875
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 29500
// misc. shooting
SWEP.Firemodes = {1, 2}
SWEP.RPM = 700
SWEP.Spread = 0.0005
SWEP.ShootTimeMult = 0.4
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 7
SWEP.RecoilResetTime = 0.04
SWEP.RecoilDissipationRate = 13
SWEP.RecoilFirstShotMult = 0.75
SWEP.RecoilVisualKick = 1.5
SWEP.RecoilKick = 8
SWEP.RecoilStability = 0.7
SWEP.RecoilSpreadPenalty = 0.005
SWEP.HipFireSpreadPenalty = 0.06
SWEP.PeekPenaltyFraction = 0.2
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.875
SWEP.ShootingSpeedMult = 0.75
SWEP.SightedSpeedMult = 0.6
SWEP.ReloadSpeedMult = 0.4
SWEP.AimDownSightsTime = 0.4
SWEP.SprintToFireTime = 0.42
SWEP.Sway = 1.5
SWEP.ScopedSway = 0.1
SWEP.FreeAimMaxAngle = 5.5
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0.05, 0, 0)
SWEP.SightPos = Vector(-4.495, -7.5, -4.17)
SWEP.CorrectivePos = Vector(0, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 20
SWEP.DefaultAmmo = 0
SWEP.Ammo = "ar2"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint/magazines/g36k.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.3
SWEP.DropMagazineTime = 0.3
// sounds
local path = "tacrp/weapons/hk417/"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Sound_Shoot_Silenced = "tacrp/weapons/sg551/sg551_fire_silenced-1.wav"
SWEP.Vol_Shoot = 110
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["fire_iron"] = "dryfire",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -1, -0.1),
vm_ang = Angle(0, 0.4, 0),
t = 0.25,
tmax = 0.25,
}
// attachments
SWEP.AttachmentElements = {
["sights"] = {
BGs_VM = {
{1, 1}
},
},
["foldstock"] = {
BGs_VM = {
{2, 1}
},
BGs_WM = {
{1, 1}
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium", "optic_sniper"},
Bone = "ValveBiped._ROOT_HK417",
InstalledElements = {"sights"},
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.85,
Pos_VM = Vector(-4.7, 0.6, 5),
Pos_WM = Vector(10, 1.25, -6.25),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, 0, 180),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped._ROOT_HK417",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
Pos_VM = Vector(-2.9, 0.6, 24),
Pos_WM = Vector(27, 1.25, -4.25),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, 0, 180),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped._ROOT_HK417",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
Pos_VM = Vector(-3, -0.35, 15),
Pos_WM = Vector(19, 2.25, -4.4),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, 0, 90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock2", "acc_extmag_rifle2", "acc_sling", "acc_duffle", "acc_bipod"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_hk417.clip_out", path .. "clip_out.wav")
addsound("tacint_hk417.clip_in", path .. "clip_in.wav")
addsound("tacint_hk417.bolt_action", path .. "bolt_action.wav")
addsound("tacint_hk417.bolt_latch", path .. "bolt_latch.wav")
addsound("tacint_hk417.fire_select", path .. "fire_select.wav")
addsound("tacint_hk417.Buttstock_Back", path .. "buttstock_back.wav")

View File

@@ -0,0 +1,360 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Desert Eagle"
SWEP.AbbrevName = "Deagle"
SWEP.Category = "[FT] Оружие" // "Tactical RP (Extras)"
SWEP.SubCatTier = "1Elite"
SWEP.SubCatType = "2Magnum Pistol"
SWEP.Description = "Imposing magnum pistol, as iconic as it gets.\nPowerful and high capacity, but recoil is hard to manage."
SWEP.Description_Quote = "\"You hear that, Mr. Anderson?\""
SWEP.Trivia_Caliber = ".50 AE"
SWEP.Trivia_Manufacturer = "Magnum Research"
SWEP.Trivia_Year = "1983"
SWEP.Faction = TacRP.FACTION_NEUTRAL
SWEP.Credits = [[
Model: Vashts1985
Texture: Racer445
Sounds:Vunsunta, XLongWayHome
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_extras/v_deagle.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_deagle.mdl"
SWEP.Slot = 1
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 75,
Damage_Min = 45,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 45,
Damage_Min = 20,
Range_Min = 100,
Range_Max = 1500,
RPM = 150,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1.125,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.75
},
RecoilDissipationRate = 4.5,
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 65,
Damage_Min = 30,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilDissipationRate = 20
}
}
// "ballistics"
SWEP.Damage_Max = 80
SWEP.Damage_Min = 50
SWEP.Range_Min = 150
SWEP.Range_Max = 1500
SWEP.Penetration = 10 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.85
SWEP.ArmorBonus = 5
SWEP.MuzzleVelocity = 10000
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.75
}
// misc. shooting
SWEP.Firemode = 1
SWEP.RPM = 150
SWEP.Spread = 0.009
SWEP.ShootTimeMult = 0.7
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 4
SWEP.RecoilResetTime = 0.3
SWEP.RecoilDissipationRate = 5
SWEP.RecoilFirstShotMult = 0.9
SWEP.RecoilVisualKick = 5
SWEP.RecoilKick = 15
SWEP.RecoilStability = 0.5
SWEP.RecoilAltMultiplier = 100
SWEP.RecoilSpreadPenalty = 0.02
SWEP.HipFireSpreadPenalty = 0.02
SWEP.PeekPenaltyFraction = 0.125
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.9
SWEP.ShootingSpeedMult = 0.75
SWEP.SightedSpeedMult = 0.8
SWEP.ReloadSpeedMult = 0.75
SWEP.AimDownSightsTime = 0.32
SWEP.SprintToFireTime = 0.27
SWEP.Sway = 1.5
SWEP.ScopedSway = 0.6
SWEP.FreeAimMaxAngle = 4.5
// hold types
SWEP.HoldType = "revolver"
SWEP.HoldTypeSprint = "normal"
SWEP.HoldTypeBlindFire = "pistol"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_PISTOL
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_PISTOL
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(0, -2, -5)
SWEP.SprintAng = Angle(0, 30, 0)
SWEP.SprintPos = Vector(2, 0, -12)
SWEP.SightAng = Angle(-0.05, -0.1, 0)
SWEP.SightPos = Vector(-3.28, 0, -4)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.CorrectivePos = Vector(0, 0, 0.1)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_PISTOL
SWEP.HolsterPos = Vector(0, 3, -4)
SWEP.HolsterAng = Angle(90, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 7
SWEP.DefaultAmmo = 0
SWEP.Ammo = "357"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1.4
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/deagle.mdl"
SWEP.DropMagazineImpact = "pistol"
SWEP.ReloadUpInTime = 0.95
SWEP.DropMagazineTime = 0.25
// sounds
local path = "tacint_extras/degala/"
local path1 = "tacrp/weapons/gsr1911/"
SWEP.Sound_Shoot = path .. "deagle-1.wav"
SWEP.Vol_Shoot = 110
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
SWEP.EjectEffect = 1
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 4
SWEP.MuzzleEffect = "muzzleflash_pistol_deagle"
// anims
// VM:
// idle
// fire
// fire1, fire2...
// dryfire
// melee
// reload
// midreload
// prime_grenade
// throw_grenade
// throw_grenade_underhand
// deploy
// blind_idle
// blind_fire
// blind_fire1, blind_fire2...
// blind_dryfire
// WM:
// attack1
SWEP.AnimationTranslationTable = {
["deploy"] = "draw",
["fire"] = {"shoot1", "shoot2", "shoot3"},
["blind_fire"] = {"blind_shoot1", "blind_shoot2", "blind_shoot3"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -2, -1.75),
vm_ang = Angle(0, 8, 0),
t = 0.4,
tmax = 0.5,
bones = {
{
bone = "ValveBiped.slide",
pos = Vector(0, 0, -3),
t0 = 0,
t1 = 0.35,
},
{
bone = "ValveBiped.hammer",
ang = Angle(-15, 0, 0),
t0 = 0,
t1 = 0.1,
},
{
bone = "ValveBiped.Bip01_R_Finger1",
ang = Angle(0, -15, 0),
t0 = 0,
t1 = 0.1,
},
{
bone = "ValveBiped.Bip01_R_Finger11",
ang = Angle(-35, 0, 0),
t0 = 0,
t1 = 0.15,
},
},
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.Magnum
SWEP.LastShot = true
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium"},
Bone = "ValveBiped.GSR1911_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
VMScale = 1,
WMScale = 1,
Pos_VM = Vector(-3.8, 0, 5.55),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, -1, -0.85),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = {"barrel"},
Bone = "ValveBiped.GSR1911_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
VMScale = 0.4,
WMScale = 0.5,
Pos_VM = Vector(-0.76, 0.7, 7.35),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 9.25, -1.5),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.GSR1911_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
VMScale = 1.1,
WMScale = 1.3,
Pos_VM = Vector(-1.7, 0, 7),
Ang_VM = Angle(90, 0, 180),
Pos_WM = Vector(0, 5, -3),
Ang_WM = Angle(0, -90, 180),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_extmag_pistol2", "acc_holster", "acc_brace"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_semi"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_pistol"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_degala.clip_in", path .. "clip_in.wav")
addsound("tacint_degala.clip_in-mid", path1 .. "gsr1911_clip_in-mid.wav")
addsound("tacint_degala.clip_out", path .. "clip_out.wav")
addsound("tacint_degala.slide_action", path1 .. "gsr1911_slide_action.wav")
addsound("tacint_degala.slide_shut", path .. "sliderelease.wav")
addsound("tacint_degala.cock_hammer", path1 .. "gsr1911_cockhammer.wav")

View File

@@ -0,0 +1,348 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "FN Five-seveN"
SWEP.AbbrevName = "Five-seveN"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "1Elite"
SWEP.SubCatType = "1Pistol"
SWEP.Description = "Bulky PDW caliber pistol with excellent capacity.\nHigh velocity rounds retain effectiveness at range and pierces armor easily."
SWEP.Description_Quote = "The notorious \"mata-policias.\"" -- The Five-seveN has large purchase among Mexican cartels. The nickname translates to "cop-killer."
SWEP.Trivia_Caliber = "5.7x28mm"
SWEP.Trivia_Manufacturer = "FN Herstal"
SWEP.Trivia_Year = "1998"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = [[
Assets: Counter-Strike: Online 2, edited by speedonerd
Sounds: Vunsunta, Counter-Strike: Online 2
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_shark/v_57.mdl"
SWEP.WorldModel = "models/weapons/tacint_shark/w_57.mdl"
SWEP.Slot = 1
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 22,
Damage_Min = 20,
RPM = 500,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 20,
Damage_Min = 16,
RPM = 240,
RecoilMaximum = 5,
RecoilResetTime = 0.22,
RecoilDissipationRate = 7,
RecoilSpreadPenalty = 0.0075,
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 14,
Damage_Min = 12,
RPM = 600,
},
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.Pistol
// "ballistics"
SWEP.Damage_Max = 27
SWEP.Damage_Min = 20
SWEP.Range_Min = 1200
SWEP.Range_Max = 3000
SWEP.Penetration = 10 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.95
SWEP.ArmorBonus = 2
SWEP.MuzzleVelocity = 22500
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
// misc. shooting
SWEP.Firemode = 1
SWEP.RPM = 550
SWEP.RPMMultSemi = 0.65
SWEP.Spread = 0.001
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 8
SWEP.RecoilResetTime = 0.2
SWEP.RecoilDissipationRate = 12
SWEP.RecoilFirstShotMult = 1 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 1
SWEP.RecoilKick = 4
SWEP.RecoilStability = 0.2
SWEP.RecoilSpreadPenalty = 0.0025
SWEP.HipFireSpreadPenalty = 0.025
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.975
SWEP.ShootingSpeedMult = 0.85
SWEP.SightedSpeedMult = 0.8
SWEP.ReloadSpeedMult = 0.75
SWEP.AimDownSightsTime = 0.28
SWEP.SprintToFireTime = 0.28
SWEP.Sway = 1
SWEP.ScopedSway = 0.5
SWEP.FreeAimMaxAngle = 4
// hold types
SWEP.HoldType = "revolver"
SWEP.HoldTypeSprint = "normal"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_PISTOL
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_PISTOL
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0.25, -2, -5.25)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(0, -2, -5)
SWEP.BlindFireSuicideAng = Angle(-130, 0, 45)
SWEP.BlindFireSuicidePos = Vector(25, 15, -6)
SWEP.SprintAng = Angle(0, 30, 0)
SWEP.SprintPos = Vector(2, 0, -12)
SWEP.SightAng = Angle(0.1, 0.55, 0)
SWEP.SightPos = Vector(-3.44, 0, -3.75)
SWEP.CorrectivePos = Vector(0, 0, 0)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_PISTOL
SWEP.HolsterPos = Vector(0, 3, -4)
SWEP.HolsterAng = Angle(90, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 20
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.Ammo_Expanded = "ti_pdw"
SWEP.ReloadTimeMult = 1.35
SWEP.DropMagazineModel = "models/weapons/tacint_shark/magazines/57.mdl"
SWEP.DropMagazineImpact = "pistol"
SWEP.ReloadUpInTime = 0.85
SWEP.DropMagazineTime = 0.2
// sounds
local path = "tacrp/weapons/p2000/p2000_"
local path1 = "tacint_shark/57/"
SWEP.Sound_Shoot = "^" .. path1 .. "fiveseven-1.wav"
SWEP.Sound_Shoot_Silenced = path1 .. "usp1.wav"
SWEP.Vol_Shoot = 110
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 4
SWEP.EjectEffect = 2
SWEP.MuzzleEffect = "muzzleflash_pistol"
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "draw",
["fire_iron"] = "shoot2",
["fire"] = {"shoot1", "shoot2", "shoot3"},
["blind_fire"] = {"blind_shoot1", "blind_shoot2", "blind_shoot3"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.5, -0.7),
vm_ang = Angle(0, 2, 0),
t = 0.2,
tmax = 0.2,
bones = {
{
bone = "ValveBiped.slide",
pos = Vector(0, 0, -3),
t0 = 0,
t1 = 0.2,
},
{
bone = "ValveBiped.hammer",
ang = Angle(-15, 0, 0),
t0 = 0,
t1 = 0.15,
},
{
bone = "ValveBiped.Bip01_R_Finger1",
ang = Angle(0, -15, 0),
t0 = 0,
t1 = 0.1,
},
{
bone = "ValveBiped.Bip01_R_Finger11",
ang = Angle(-35, 0, 0),
t0 = 0,
t1 = 0.15,
},
},
}
SWEP.NoIdle = true
SWEP.ShootTimeMult = 0.5
SWEP.LastShot = true
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = "optic_pistol",
Bone = "ValveBiped.slide",
WMBone = "Box01",
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 1,
WMScale = 1,
Pos_VM = Vector(0.04, 0.25, -0.4),
Ang_VM = Angle(0, 90, 180),
Pos_WM = Vector(-0.2, -1, -0.75),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.p2000_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
VMScale = 0.55,
WMScale = 0.6,
Pos_VM = Vector(-3.2, -0.05, 10),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(-0.1, 9, -1.5),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.p2000_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
VMScale = 1.1,
WMScale = 1.3,
Pos_VM = Vector(-2, -0.05, 6),
Ang_VM = Angle(90, 0, 180),
Pos_WM = Vector(-0.2, 5, -2.75),
Ang_WM = Angle(0, -90, 180),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_extmag_pistol", "acc_holster", "acc_brace"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_semi"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_57.clip_in", path1 .. "p228_clipin.wav")
addsound("tacint_57.clip_in-mid", path1 .. "p228_clipin.wav")
addsound("tacint_57.clip_out", path1 .. "magout.wav")
addsound("tacint_57.slide_action", path1 .. "fiveseven_slidepull.wav")
addsound("tacint_57.slide_shut", path1 .. "sliderelease.wav")
addsound("tacint_57.cock_hammer", path .. "cockhammer.wav")

View File

@@ -0,0 +1,356 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Glock 18C"
SWEP.Category = "[FT] Оружие" // "Tactical RP (Extras)"
SWEP.SubCatTier = "3Security"
SWEP.SubCatType = "3Machine Pistol"
SWEP.Description = "Machine pistol with high fire rate and mobility."
SWEP.Description_Quote = "\"Sooner or later, you'll have to jump.\""
SWEP.Trivia_Caliber = "9x19mm"
SWEP.Trivia_Manufacturer = "Glock Ges.m.b.H"
SWEP.Trivia_Year = "1982"
SWEP.Faction = TacRP.FACTION_NEUTRAL
SWEP.Credits = [[
Model: Hav0k101
Texture: el maestro de graffiti
Sound: BlitzBoaR, Lorn, Ghost597879, Zeven II
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_extras/v_glock18.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_glock18.mdl"
SWEP.Slot = 1
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 20,
Damage_Min = 6,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 10,
Damage_Min = 4,
Range_Min = 200,
Range_Max = 1750,
RPM = 1000,
HipFireSpreadPenalty = 0.015,
RecoilMaximum = 10,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 6,
Damage_Min = 2,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilDissipationRate = 25,
RecoilMaximum = 10
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.MachinePistol
// "ballistics"
SWEP.Damage_Max = 18
SWEP.Damage_Min = 6
SWEP.Range_Min = 400
SWEP.Range_Max = 1500
SWEP.Penetration = 3
SWEP.ArmorPenetration = 0.425
SWEP.ArmorBonus = 0.5
SWEP.MuzzleVelocity = 10500
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
}
// misc. shooting
SWEP.Firemodes = {2, 1}
SWEP.RPM = 1000
SWEP.Spread = 0.011
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 7
SWEP.RecoilResetTime = 0.1
SWEP.RecoilDissipationRate = 15
SWEP.RecoilFirstShotMult = 1 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 2
SWEP.RecoilKick = 4
SWEP.RecoilSpreadPenalty = 0.005
SWEP.HipFireSpreadPenalty = 0.024
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.975
SWEP.ShootingSpeedMult = 0.75
SWEP.SightedSpeedMult = 0.8
SWEP.ReloadSpeedMult = 0.75
SWEP.AimDownSightsTime = 0.25
SWEP.SprintToFireTime = 0.25
SWEP.Sway = 1
SWEP.ScopedSway = 0.5
SWEP.FreeAimMaxAngle = 3
// hold types
SWEP.HoldType = "revolver"
SWEP.HoldTypeSprint = "normal"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_PISTOL
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_PISTOL
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(0, -2, -5)
SWEP.BlindFireSuicideAng = Angle(-125, 0, 45)
SWEP.BlindFireSuicidePos = Vector(25, 12, -5)
SWEP.SprintAng = Angle(0, 30, 0)
SWEP.SprintPos = Vector(2, 0, -12)
SWEP.SightAng = Angle(0, 0, 0)
SWEP.SightPos = Vector(-3.31, 0, -3.2)
SWEP.CorrectivePos = Vector(0.02, -1, 0)
SWEP.CorrectiveAng = Angle(0.05, -0.05, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_PISTOL
SWEP.HolsterPos = Vector(0, 3, -4)
SWEP.HolsterAng = Angle(90, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "pistol"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1.4
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/glock.mdl"
SWEP.DropMagazineImpact = "pistol"
SWEP.ReloadUpInTime = 0.85
SWEP.DropMagazineTime = 0.2
// sounds
local path = "tacrp/weapons/p2000/p2000_"
local path2 = "tacint_extras/glock18/"
SWEP.Sound_Shoot = "^" .. path2 .. "glock18-1.wav"
SWEP.Sound_Shoot_Silenced = "tacrp_extras/glock/" .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 110
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 4
SWEP.MuzzleEffect = "muzzleflash_pistol"
SWEP.EjectEffect = 1
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "draw",
["fire_iron"] = "shoot2",
["fire"] = {"shoot1", "shoot2", "shoot3"},
["blind_fire"] = {"blind_shoot1", "blind_shoot2", "blind_shoot3"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.5, -0.6),
vm_ang = Angle(0, 2, 0),
t = 0.2,
tmax = 0.2,
bones = {
{
bone = "ValveBiped.slide",
pos = Vector(0, 0, -3),
t0 = 0,
t1 = 0.2,
},
{
bone = "ValveBiped.hammer",
ang = Angle(-15, 0, 0),
t0 = 0,
t1 = 0.15,
},
{
bone = "ValveBiped.Bip01_R_Finger1",
ang = Angle(0, -15, 0),
t0 = 0,
t1 = 0.1,
},
{
bone = "ValveBiped.Bip01_R_Finger11",
ang = Angle(-35, 0, 0),
t0 = 0,
t1 = 0.15,
},
},
}
SWEP.NoIdle = true
SWEP.ShootTimeMult = 0.4
SWEP.LastShot = true
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = "optic_pistol",
Bone = "ValveBiped.slide",
WMBone = "ValveBiped.Bip01_R_Hand", // someone forgor to rig the box bone
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.9,
WMScale = 1.2,
Pos_VM = Vector(0.21, 0.7, -0.05),
Ang_VM = Angle(0, 90, 180),
Pos_WM = Vector(2, 1.2, -4.5),
Ang_WM = Angle(180, 0, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.barrel_assembly",
WMBone = "ValveBiped.Bip01_R_Hand",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
VMScale = 0.5,
WMScale = 0.6,
Pos_VM = Vector(-0.5, 0.25, 7),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(14.2, 1.2, -4.25),
Ang_WM = Angle(0, 0, 180),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.p2000_rootbone",
WMBone = "ValveBiped.Bip01_R_Hand",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
VMScale = 1.1,
WMScale = 1.2,
Pos_VM = Vector(-2.1, -0.23, 6.6),
Ang_VM = Angle(90, 0, 180),
Pos_WM = Vector(10.5, 1.2, -2.75),
Ang_WM = Angle(0, 0, 0),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_extmag_smg", "acc_holster", "acc_brace"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_pistol"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_extras_glock18.clip_in", path2 .. "Clipin.wav")
addsound("tacint_extras_glock18.clip_in-mid", path .. "clip_in-mid.wav")
addsound("tacint_extras_glock18.clip_out", path2 .. "Clipout.wav")
addsound("tacint_extras_glock18.slide_action", path .. "slide_action.wav")
addsound("tacint_extras_glock18.slide_shut", path .. "slide_shut.wav")
addsound("tacint_extras_glock18.cock_hammer", path .. "cockhammer.wav")

View File

@@ -0,0 +1,408 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Karabiner 98k"
SWEP.AbbrevName = "Kar98k"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "5Value"
SWEP.SubCatType = "6Marksman Rifle"
SWEP.Description = "Antique bolt-action rifle with an enduring design. Powerful up close, but is essentially obsolete on the modern battlefield."
SWEP.Description_Quote = "\"Do you want total war?\""
SWEP.Trivia_Caliber = "7.92x57mm Mauser"
SWEP.Trivia_Manufacturer = "Mauser"
SWEP.Trivia_Year = "1935"
SWEP.Faction = TacRP.FACTION_MILITIA
SWEP.Credits = [[
Model: Day of Defeat: Source, edited by 8Z
Texture: Cafe Rev., rascal, 5hifty
Sound: rzen1th
Animations: speedonerd
]]
SWEP.ViewModel = "models/weapons/tacint_extras/v_k98.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_k98.mdl"
SWEP.Slot = 2
SWEP.SlotAlt = 3
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 80,
Damage_Min = 55,
HipFireSpreadPenalty = 0.03,
Spread = 0.002,
RPM = 50,
ShootTimeMult = 0.75,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 0.75,
[HITGROUP_RIGHTARM] = 0.75,
[HITGROUP_LEFTLEG] = 0.5,
[HITGROUP_RIGHTLEG] = 0.5,
[HITGROUP_GEAR] = 0.5
},
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 70,
Damage_Min = 30,
Range_Min = 500,
Range_Max = 4000,
RPM = 35,
ShootTimeMult = 1.1,
Spread = 0.001,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.75,
[HITGROUP_RIGHTARM] = 0.75,
[HITGROUP_LEFTLEG] = 0.5,
[HITGROUP_RIGHTLEG] = 0.5,
[HITGROUP_GEAR] = 0.5
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 50,
Damage_Min = 30,
},
[TacRP.BALANCE_OLDSCHOOL] = {
HipFireSpreadPenalty = 0.01,
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.SniperRifle
// "ballistics"
SWEP.Damage_Max = 85
SWEP.Damage_Min = 46
SWEP.Range_Min = 300
SWEP.Range_Max = 2800
SWEP.Penetration = 12
SWEP.ArmorPenetration = 0.8
SWEP.ArmorBonus = 1
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.75,
[HITGROUP_RIGHTARM] = 0.75,
[HITGROUP_LEFTLEG] = 0.5,
[HITGROUP_RIGHTLEG] = 0.5,
[HITGROUP_GEAR] = 0.5
}
SWEP.MuzzleVelocity = 32000
// misc. shooting
SWEP.Firemode = 1
SWEP.FiremodeName = "Bolt-Action" // only used externally for firemode name distinction
SWEP.RPM = 45
SWEP.Spread = 0.004 // WW2 rifles weren't all that accurate...
SWEP.HipFireSpreadPenalty = 0.04
SWEP.PeekPenaltyFraction = 0.3
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 1
SWEP.RecoilResetTime = 0.2
SWEP.RecoilDissipationRate = 1
SWEP.RecoilFirstShotMult = 1 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 5
SWEP.RecoilKick = 5
SWEP.RecoilSpreadPenalty = 0 // extra spread per one unit of recoil
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.85
SWEP.ShootingSpeedMult = 0.75
SWEP.SightedSpeedMult = 0.55
SWEP.ReloadSpeedMult = 0.3
SWEP.AimDownSightsTime = 0.34
SWEP.SprintToFireTime = 0.4
SWEP.Sway = 1
SWEP.ScopedSway = 0.1
SWEP.FreeAimMaxAngle = 7
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.HoldTypeNPC = "shotgun"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_CROSSBOW
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SHOTGUN
SWEP.PassiveAng = Angle(0, 2, 0)
SWEP.PassivePos = Vector(0, 1, -0.5)
SWEP.BlindFireAng = Angle(0, 0, -45)
SWEP.BlindFirePos = Vector(1, 0, 5)
SWEP.BlindFireLeftAng = Angle(75, 0, -20)
SWEP.BlindFireLeftPos = Vector(8, 10, -2)
SWEP.BlindFireRightAng = Angle(-75, 0, -45)
SWEP.BlindFireRightPos = Vector(-9, 17, -5)
SWEP.BlindFireSuicideAng = Angle(0, 115, 0)
SWEP.BlindFireSuicidePos = Vector(-4.5, 25, -45)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(2, 4.5, 0.75)
SWEP.SightAng = Angle(0, 0.4, 0)
SWEP.SightPos = Vector(-4.72, 1, 2.15)
SWEP.CorrectivePos = Vector(0.05, 0, 0.2)
SWEP.CorrectiveAng = Angle(0.1, -0.3, 0)
SWEP.CustomizePos = Vector(4, 3, -1.5)
SWEP.CustomizeAng = Angle(30, 15, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK2
SWEP.HolsterPos = Vector(5, 4, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// scope
SWEP.Scope = true
SWEP.ScopeFOV = 90 / 1.25
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 5
SWEP.DefaultAmmo = 0
SWEP.Ammo = "ar2"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.Ammo_Expanded = "ti_rifle"
SWEP.ShotgunReload = true
SWEP.ShotgunThreeload = false
SWEP.ShotgunFullCancel = true
SWEP.ShotgunNoReverseStart = true
SWEP.ReloadTimeMult = 0.8
SWEP.ShootTimeMult = 0.65
SWEP.DropMagazineModel = false
SWEP.ShotgunUpInTime = 2.3
SWEP.ReloadUpInTime = 2.2
SWEP.BulletBodygroups = {
[1] = {1, 1},
[2] = {1, 0},
}
// sounds
// local path = "TacRP/weapons/spr/"
local path1 = "tacint_extras/k98/"
SWEP.Sound_Shoot = "^" .. path1 .. "scout_fire-1.wav"
SWEP.Sound_Shoot_Silenced = "TacRP/weapons/ak47/ak47_fire_silenced-1.wav"
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_1"
SWEP.EjectEffect = 2
SWEP.EjectDelay = 0.7
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "draw",
["fire"] = {"shoot1", "shoot2"},
["blind_idle"] = "idle",
["blind_dryfire"] = "dryfire",
["blind_fire"] = "shoot1",
["reload"] = "reload",
["reload_finish"] = "reload_end",
["reload_clip"] = "reload_clip",
["melee"] = {"melee1", "melee2"},
--["melee"] = "melee_bayonet",
["dryfire"] = "dryfire",
["jam"] = "reload_end"
}
// attachments
SWEP.AttachmentElements = {
["optic"] = {
BGs_VM = {
{2, 1}
},
BGs_WM = {
{1, 1}
},
},
["optic_clip"] = {
BGs_VM = {
{2, 0}
},
BGs_WM = {
{1, 0}
},
},
["scope"] = {
BGs_VM = {
{2, 2}
},
BGs_WM = {
{1, 2},
{2, 1}
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Top",
Category = {"optic_cqb_nookp7", "optic_okp7", "optic_medium", "optic_kar98", "stripper_clip"},
WMBone = "Bone02",
Bone = "k98_root",
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
InstalledElements = {"optic"},
VMScale = 0.9,
Pos_VM = Vector(0.05, -2.8, 7),
Ang_VM = Angle(90, 0, -90),
Pos_WM = Vector(0, 1.25, -5.6),
Ang_WM = Angle(0, 0, 180),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
WMBone = "Bone02",
Bone = "k98_root",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
VMScale = 0.75,
WMScale = 0.75,
Pos_VM = Vector(-0.03, -1.45, 34),
Pos_WM = Vector(25.5, 1.2, -4.9),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, 0, 180),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom"},
WMBone = "Bone02",
Bone = "k98_root",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
Pos_VM = Vector(-0.5, -1, 22),
Pos_WM = Vector(8, 2, -4),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, 0, 90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_sling", "acc_duffle", "acc_bipod"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_manual"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_manual"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = CHAN_AUTO,
volume = 1.0,
sound = spath
})
end
addsound("tacint_extras_k98.Clip_Out", path1 .. "magout.wav")
addsound("tacint_extras_k98.Clip_In", path1 .. "magin.wav")
addsound("tacint_extras_k98.CockBack", path1 .. "boltback.wav")
addsound("tacint_extras_k98.CockForward", path1 .. "boltforward.wav")
addsound("tacint_extras_k98.safety", path1 .. "magrelease.wav")
addsound("tacint_extras_k98.InsertShell", path1 .. "roundinsert.wav")
addsound("tacint_extras_k98.ClipIn", path1 .. "clipin2.wav")
addsound("tacint_extras_k98.ClipIn2", path1 .. "roundinsert_clip.wav")
addsound("tacint_extras_k98.bolt_up", path1 .. "boltup.wav")
addsound("tacint_extras_k98.bolt_down", path1 .. "boltdown.wav")
--addsound("tacint_extras_k98.bolt_up", path1 .. "boltlatch.wav")
--addsound("tacint_extras_k98.bolt_down", path1 .. "boltrelease.wav")

View File

@@ -0,0 +1,360 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "SIG P226" // Apparently this is specifically the XM25 model adopted by the Navy SEALs but i dont wanna specify it
SWEP.AbbrevName = "P226"
SWEP.Category = "[FT] Оружие" // "Tactical RP (Extras)"
SWEP.SubCatTier = "3Security"
SWEP.SubCatType = "1Pistol"
SWEP.Description = "Handgun with superior range and precision but low capacity."
SWEP.Description_Quote = "\"The correct term is 'babes,' sir.\""
SWEP.Trivia_Caliber = ".40 S&W" // ... because the XM25 is 9mm only and doesn't come in 13 rounders
SWEP.Trivia_Manufacturer = "SIG Sauer AG"
SWEP.Trivia_Year = "1984"
SWEP.Faction = TacRP.FACTION_NEUTRAL
SWEP.Credits = [[
Model: SoulSlayer
Texture: Thanez
Sound: Anders, DMG, FxDarkloki, & Thanez
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_extras/v_p226.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_p226.mdl"
SWEP.Slot = 1
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 28,
Damage_Min = 20,
Range_Min = 1200,
Range_Max = 3000,
RPM = 450,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.75
},
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 24,
Damage_Min = 16,
Range_Min = 750,
Range_Max = 3000,
ClipSize = 10,
RPM = 180,
RPMMultSemi = 1,
RecoilMaximum = 4,
RecoilResetTime = 0.2,
RecoilDissipationRate = 5,
RecoilFirstShotMult = 1,
RecoilSpreadPenalty = 0.008,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.Pistol
// "ballistics"
SWEP.Damage_Max = 25
SWEP.Damage_Min = 15
SWEP.Range_Min = 800
SWEP.Range_Max = 2500
SWEP.Penetration = 6 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.75
SWEP.ArmorBonus = 1
SWEP.MuzzleVelocity = 14000
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.75
}
// misc. shooting
SWEP.Firemode = 1
SWEP.RPM = 380
SWEP.RPMMultSemi = 0.75
SWEP.Spread = 0.001
SWEP.ShootTimeMult = 0.5
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 5
SWEP.RecoilResetTime = 0.2
SWEP.RecoilDissipationRate = 7
SWEP.RecoilFirstShotMult = 1
SWEP.RecoilVisualKick = 1.5
SWEP.RecoilKick = 3.5
SWEP.RecoilStability = 0.35
SWEP.RecoilSpreadPenalty = 0.0025
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.975
SWEP.ShootingSpeedMult = 0.9
SWEP.SightedSpeedMult = 0.8
SWEP.ReloadSpeedMult = 0.75
SWEP.AimDownSightsTime = 0.25
SWEP.SprintToFireTime = 0.25
SWEP.Sway = 1
SWEP.ScopedSway = 0.5
SWEP.FreeAimMaxAngle = 3
// hold types
SWEP.HoldType = "revolver"
SWEP.HoldTypeSprint = "normal"
SWEP.HoldTypeBlindFire = "pistol"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_PISTOL
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_PISTOL
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(0, -2, -5)
SWEP.SprintAng = Angle(0, 30, 0)
SWEP.SprintPos = Vector(2, 0, -12)
SWEP.SightAng = Angle(0.02, 0.15, 0)
SWEP.SightPos = Vector(-3.45, 0, -3.35)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_PISTOL
SWEP.HolsterPos = Vector(0, 3, -4)
SWEP.HolsterAng = Angle(90, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 13
SWEP.DefaultAmmo = 0
SWEP.Ammo = "pistol"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.Ammo_Expanded = "ti_pistol_heavy"
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/p226.mdl"
SWEP.DropMagazineImpact = "pistol"
SWEP.ReloadUpInTime = 0.85
SWEP.DropMagazineTime = 0.2
// sounds
local path = "tacint_extras/p226/"
local path1 = "tacrp/weapons/p250/p250_"
SWEP.Sound_Shoot = "^" .. path .. "p228-1.wav"
SWEP.Sound_Shoot_Silenced = path1 .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 110
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 4
SWEP.MuzzleEffect = "muzzleflash_pistol"
SWEP.EjectEffect = 1
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "draw",
["fire"] = {"shoot1", "shoot2", "shoot3"},
["blind_fire"] = {"blind_shoot1", "blind_shoot2", "blind_shoot3"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.5, -0.6),
vm_ang = Angle(0, 2, 0),
t = 0.2,
tmax = 0.2,
bones = {
{
bone = "ValveBiped.slide",
pos = Vector(0, 0, -3),
t0 = 0,
t1 = 0.2,
},
{
bone = "ValveBiped.hammer",
ang = Angle(-15, 0, 0),
t0 = 0,
t1 = 0.15,
},
{
bone = "ValveBiped.Bip01_R_Finger1",
ang = Angle(0, -15, 0),
t0 = 0,
t1 = 0.1,
},
{
bone = "ValveBiped.Bip01_R_Finger11",
ang = Angle(-35, 0, 0),
t0 = 0,
t1 = 0.15,
},
},
}
SWEP.LastShot = true
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = "optic_pistol",
Bone = "ValveBiped.slide",
WMBone = "Box01",
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
VMScale = 1,
WMScale = 1.2,
Pos_VM = Vector(0.01, -0.3, -0.1),
Ang_VM = Angle(0, 90, 180),
Pos_WM = Vector(0.04, -1.4, -1),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.barrel_assembly",
WMBone = "Box01",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
VMScale = 0.5,
WMScale = 0.5,
Pos_VM = Vector(-0.6, 0.43, 6.4),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 8.2, -1.5),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.p250_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
VMScale = 1.1,
WMScale = 1,
Pos_VM = Vector(-2, 0, 5.25),
Ang_VM = Angle(90, 0, 180),
Pos_WM = Vector(0, 4.5, -2.9),
Ang_WM = Angle(0, -90, 180),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_extmag_pistol", "acc_holster", "acc_brace"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_semi"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_pistol"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_p226.clip_in", path .. "magshove.wav")
addsound("tacint_p226.clip_in-mid", path .. "magshove.wav")
addsound("tacint_p226.clip_out", path .. "magout.wav")
addsound("tacint_p226.slide_action", path1 .. "slide_action.wav")
addsound("tacint_p226.slide_shut", path .. "sliderelease.wav")
addsound("tacint_p226.cock_hammer", path .. "cockhammer.wav")

View File

@@ -0,0 +1,359 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "РПК-74"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "3Security"
SWEP.SubCatType = "5Machine Gun"
SWEP.Description = "Light machine gun derived from an infantry rifle. High damage and good recoil, but mobility and spread is poor."
SWEP.Description_Quote = "A simple yet effective concept."
SWEP.Trivia_Caliber = "7.62x39mm"
SWEP.Trivia_Manufacturer = "Molot" // I checked, neither Izhmash nor Tula ever manufactured the original RPK.
SWEP.Trivia_Year = "1961"
SWEP.Faction = TacRP.FACTION_MILITIA
SWEP.Credits = [[
Assets: Call To Arms
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_shark/v_rpk.mdl"
SWEP.WorldModel = "models/weapons/tacint_shark/w_rpk.mdl"
SWEP.Slot = 2
SWEP.SlotAlt = 3
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 35,
Damage_Min = 24,
Spread = 0.003,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 20,
Damage_Min = 15,
Range_Min = 800,
Range_Max = 3500,
ClipSize = 50,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 12,
Damage_Min = 5,
Spread = 0.005,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilMaximum = 20,
HipFireSpreadPenalty = 0.015
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.MachineGun
// "ballistics"
SWEP.Damage_Max = 30
SWEP.Damage_Min = 19
SWEP.Range_Min = 1000 // distance for which to maintain maximum damage
SWEP.Range_Max = 4500 // distance at which we drop to minimum damage
SWEP.Penetration = 10 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.775
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 25000
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 550
SWEP.Spread = 0.0075
SWEP.ShootTimeMult = 0.5
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 20
SWEP.RecoilResetTime = 0.22
SWEP.RecoilDissipationRate = 20
SWEP.RecoilFirstShotMult = 2 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 1
SWEP.RecoilKick = 4
SWEP.RecoilStability = 0.4
SWEP.RecoilAltMultiplier = 300
SWEP.RecoilSpreadPenalty = 0.0012
SWEP.HipFireSpreadPenalty = 0.035
SWEP.PeekPenaltyFraction = 0.25
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.875
SWEP.ShootingSpeedMult = 0.5
SWEP.SightedSpeedMult = 0.5
SWEP.ReloadSpeedMult = 0.25
SWEP.AimDownSightsTime = 0.45
SWEP.SprintToFireTime = 0.5
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -4)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0.05, -0.7, 0)
SWEP.SightPos = Vector(-4.68, -7.5, -2.9)
SWEP.CorrectivePos = Vector(0, 0, -0.05)
SWEP.CorrectiveAng = Angle(0.75, 0.7, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK2
SWEP.HolsterPos = Vector(5, 6, -8)
SWEP.HolsterAng = Angle(0, 0, 0)
SWEP.Sway = 2
SWEP.ScopedSway = 0.175
SWEP.FreeAimMaxAngle = 6
SWEP.Bipod = true
SWEP.BipodRecoil = 0.4
SWEP.BipodKick = 0.4
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 50
SWEP.DefaultAmmo = 0
SWEP.Ammo = "ar2"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1.3
SWEP.DropMagazineModel = "models/weapons/tacint_shark/magazines/rpk.mdl"
SWEP.DropMagazineImpact = "metal"
SWEP.ReloadUpInTime = 1.55
SWEP.DropMagazineTime = 0.6
// sounds
local path = "tacrp/weapons/ak47/ak47_"
local path1 = "tacint_shark/rpk/"
local path2 = "tacrp_extras/ak47/"
SWEP.Sound_Shoot = "^" .. path1 .. "shoot-2.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "unholster",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"},
["jam"] = "mid_reload",
}
SWEP.DeployTimeMult = 3
// attachments
SWEP.AttachmentElements = {
["tactical"] = {
BGs_VM = {
{2, 1}
},
BGs_WM = {
{2, 1}
},
},
["bipod"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
},
},
["akmount"] = {
BGs_VM = {
{2, 0}
},
BGs_WM = {
{2, 0}
},
AttPosMods = {
[1] = {
Pos_VM = Vector(-5.3, 0.4, 3),
Pos_WM = Vector(-0.4, 2, 0.5),
}
},
SortOrder = 2,
},
}
SWEP.NoRMR = true
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium", "optic_sniper", "optic_ak"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
InstalledElements = {"tactical"},
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.8,
Pos_VM = Vector(-5.3, 0.15, 4),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 3, 0.5),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = {"silencer", "muzz_ak"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
VMScale = 0.9,
Pos_VM = Vector(-3.35, 0.15, 33),
Pos_WM = Vector(0, 31, -1.75),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
Pos_VM = Vector(-3.2, -0.1, 25),
Pos_WM = Vector(-0.5, 19, -1.75),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, -90, 90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_sling", "acc_duffle", "extendedbelt", "acc_bipod"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_rpk.remove_clip", path1 .. "rpk_magout.wav")
addsound("tacint_rpk.insert_clip", path1 .. "rpk_magin.wav")
addsound("tacint_rpk.boltaction", path2 .. "bolt.mp3")
addsound("tacint_rpk.Buttstock_Back", path .. "buttstock_back.wav")

View File

@@ -0,0 +1,324 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Сайга-12К"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "5Shotgun"
SWEP.Description = "High capacity shotgun feeding from a box magazine, suitable for spraying down a room."
SWEP.Description_Quote = "Some people call it the SASG." -- Splinter Cell: Blacklist, Rainbow Six: Siege, and The Division 2 all do this
SWEP.Trivia_Caliber = "12 Gauge"
SWEP.Trivia_Manufacturer = "Kalashnikov Concern"
SWEP.Trivia_Year = "1997"
SWEP.Faction = TacRP.FACTION_NEUTRAL
SWEP.Credits = [[
Assets: Battlefield 3
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_shark/v_saiga.mdl"
SWEP.WorldModel = "models/weapons/tacint_shark/w_saiga.mdl"
SWEP.Slot = 2
SWEP.SlotAlt = 3
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 6,
Damage_Min = 2,
Range_Min = 200,
Range_Max = 2500,
Num = 6,
RPM = 200,
RPMMultSemi = 1,
Spread = 0.02,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AutoShotgun
// "ballistics"
SWEP.ShootTimeMult = 0.85
SWEP.Damage_Max = 12
SWEP.Damage_Min = 3
SWEP.Range_Min = 100 // distance for which to maintain maximum damage
SWEP.Range_Max = 1200 // distance at which we drop to minimum damage
SWEP.Penetration = 1 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.6
SWEP.ArmorBonus = 0.5
SWEP.Num = 6
SWEP.MuzzleVelocity = 10000
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 1.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
// misc. shooting
SWEP.Firemode = 1
SWEP.RPM = 300
SWEP.RPMMultSemi = 0.85
SWEP.PostBurstDelay = 0.1
SWEP.Spread = 0.04
SWEP.ShotgunPelletSpread = 0.03
SWEP.HipFireSpreadPenalty = 0.015
SWEP.MidAirSpreadPenalty = 0
SWEP.MoveSpreadPenalty = 0
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 5
SWEP.RecoilResetTime = 0.2
SWEP.RecoilDissipationRate = 8
SWEP.RecoilFirstShotMult = 1.25
SWEP.RecoilVisualKick = 1.5
SWEP.RecoilKick = 7
SWEP.RecoilStability = 0.25
SWEP.RecoilAltMultiplier = 150
SWEP.NoRecoilPattern = true
SWEP.RecoilSpreadPenalty = 0.009
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.9
SWEP.ShootingSpeedMult = 0.6
SWEP.SightedSpeedMult = 0.7
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.4
SWEP.SprintToFireTime = 0.44
SWEP.Sway = 1
SWEP.ScopedSway = 0.2
SWEP.FreeAimMaxAngle = 5
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_CROSSBOW
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_AR2
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -6)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(4, -2, -4)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0.05, -1, 0)
SWEP.SightPos = Vector(-4.66, -7.5, -3.05)
SWEP.CorrectivePos = Vector(0, 0, -0.05)
SWEP.CorrectiveAng = Angle(0.75, 0.7, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK2
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 8
SWEP.DefaultAmmo = 0
SWEP.Ammo = "buckshot"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1.15
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/saiga.mdl"
SWEP.DropMagazineImpact = "metal"
SWEP.ReloadUpInTime = 1.65
SWEP.DropMagazineTime = 0.65
// sounds
local path = "tacint_shark/saiga/"
local path1 = "tacrp/weapons/ak47/ak47_"
SWEP.Sound_Shoot = "^" .. path .. "12k_fire.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 0 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_m3"
SWEP.EjectEffect = 3
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "deploy",
["fire1"] = {"fire3_M", "fire3_R"},
["fire2"] = {"fire4_M", "fire4_L"},
["fire3"] = {"fire5_M", "fire5_L", "fire5_R"},
["fire4"] = {"fire5_M", "fire5_L", "fire5_R"},
["fire5"] = {"fire5_M", "fire5_L", "fire5_R"},
["fire_iron"] = "fire1_M",
["melee"] = {"melee1", "melee2"},
["jam"] = "mid_reload"
}
SWEP.DeployTimeMult = 1.1
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
}
},
["tactical"] = {
BGs_VM = {
{2, 1}
},
BGs_WM = {
{2, 1}
},
},
}
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb_nookp7", "optic_medium"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
InstalledElements = {"tactical"},
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.8,
Pos_VM = Vector(-5.25, 0.1, 5),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 2.5, 1),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
Pos_VM = Vector(-4.5, -0.2, 14),
Pos_WM = Vector(0, 19, -2),
Ang_VM = Angle(90, 0, -60),
Ang_WM = Angle(0, -90, 180),
},
[3] = {
PrintName = "Accessory",
Category = {"acc_foldstock", "acc", "acc_sling", "acc_duffle", "acc_extmag_shotgun_mag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[4] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Trigger",
Category = {"trigger_semi"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Ammo",
Category = {"ammo_shotgun2"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
}
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_saiga.remove_clip", path1 .. "remove_clip.wav")
addsound("tacint_saiga.insert_clip", path1 .. "insert_clip.wav")
addsound("tacint_saiga.boltaction", path .. "12k_boltpull.wav")
addsound("tacint_saiga.Buttstock_Back", path1 .. "buttstock_back.wav")

View File

@@ -0,0 +1,353 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "FN SCAR-H CQC"
SWEP.AbbrevName = "SCAR-H"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "5Battle Rifle"
SWEP.Description = "Compact, high mobility battle rifle with swift handling."
SWEP.Description_Quote = "\"Sand Bravo, we're reading 70 bogeys in your sector.\""
SWEP.Trivia_Caliber = "7.62x51mm"
SWEP.Trivia_Manufacturer = "FN America"
SWEP.Trivia_Year = "2004"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = [[
Assets: Counter-Strike: Online 2, edited by speedonerd
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_shark/v_scarh.mdl"
SWEP.WorldModel = "models/weapons/tacint_shark/w_scarh.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 38,
Damage_Min = 26,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 25,
Damage_Min = 12,
Range_Min = 500,
Range_Max = 2500,
RPM = 400,
RecoilResetTime = 0.125,
RecoilDissipationRate = 5,
RecoilMaximum = 5,
RecoilSpreadPenalty = 0.015,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.75,
[HITGROUP_RIGHTARM] = 0.75,
[HITGROUP_LEFTLEG] = 0.5,
[HITGROUP_RIGHTLEG] = 0.5,
[HITGROUP_GEAR] = 0.5
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 17,
Damage_Min = 12,
RPM = 450,
RecoilDissipationRate = 8,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilSpreadPenalty = 0.006,
RecoilMaximum = 10
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.BattleRifle
// "ballistics"
SWEP.Damage_Max = 38
SWEP.Damage_Min = 24
SWEP.Range_Min = 800
SWEP.Range_Max = 2800
SWEP.Penetration = 20
SWEP.ArmorPenetration = 0.8
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.35,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 26000
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 550
SWEP.Spread = 0.001
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 7
SWEP.RecoilResetTime = 0.12
SWEP.RecoilDissipationRate = 12
SWEP.RecoilFirstShotMult = 0.85
SWEP.RecoilVisualKick = 2
SWEP.RecoilKick = 6
SWEP.RecoilStability = 0.75
SWEP.RecoilSpreadPenalty = 0.005
SWEP.HipFireSpreadPenalty = 0.04
SWEP.PeekPenaltyFraction = 0.25
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.9
SWEP.ShootingSpeedMult = 0.825
SWEP.SightedSpeedMult = 0.65
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.35
SWEP.SprintToFireTime = 0.38
SWEP.Sway = 1.25
SWEP.ScopedSway = 0.1
SWEP.FreeAimMaxAngle = 5
SWEP.Bipod = false
SWEP.BipodRecoil = 0.5
SWEP.BipodKick = 0.4
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SightAng = Angle(0.07, 0.45, 0)
SWEP.SightPos = Vector(-4.36, -7, -4.77)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.CorrectivePos = Vector(0, 2, 0)
SWEP.CorrectiveAng = Angle(-0.1, 0.45, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 20
SWEP.DefaultAmmo = 0
SWEP.Ammo = "ar2"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/scarh.mdl"
SWEP.DropMagazineImpact = "metal"
SWEP.ReloadUpInTime = 1.1
SWEP.DropMagazineTime = 0.3
// sounds
local path = "tacrp/weapons/dsa58/dsa58_"
local path1 = "tacint_shark/scarh/"
SWEP.Sound_Shoot = "^" .. path1 .. "scarh-1.wav"
SWEP.Sound_Shoot_Silenced = "^" .. path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_g3"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["fire_iron"] = "dryfire",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -1, -0.1),
vm_ang = Angle(0, 0.4, 0),
t = 0.25,
tmax = 0.25,
bones = {
{
bone = "ValveBiped.bolt_cover",
pos = Vector(0, 0, -3),
t0 = 0.01,
t1 = 0.1,
},
}
}
// attachments
SWEP.AttachmentElements = {
["sights"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{4, 1}
}
},
}
SWEP.NoRMR = true
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium", "optic_sniper"},
Bone = "ValveBiped._ROOT_K1a",
WMBone = "Box01",
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
InstalledElements = {"sights"},
VMScale = 1,
Pos_VM = Vector(-5.25, 0.19, 3.5),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 2.5, 1.3),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped._ROOT_K1a",
WMBone = "Box01",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
Pos_VM = Vector(-2.85, 0.35, 23),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 21, -0.9),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped._ROOT_K1a",
WMBone = "Box01",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
VMScale = 1.1,
Pos_VM = Vector(-2.8, -0.75, 15),
Ang_VM = Angle(90, 0, -90),
Pos_WM = Vector(1, 11.5, -0.75),
Ang_WM = Angle(0, -90, -90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_sling", "acc_duffle", "acc_extmag_rifle2", "acc_bipod"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_scar.insert_clip", path1 .. "scarh_clipin.wav")
addsound("tacint_scar.insert_clip-mid", path1 .. "scarh_clipin.wav")
addsound("tacint_scar.remove_clip", path1 .. "scarh_clipout.wav")
addsound("tacint_scar.Handle_FoldDown", path .. "handle_folddown.wav")
addsound("tacint_scar.bolt_back", path1 .. "scarh_boltpull.wav")
addsound("tacint_scar.bolt_release", path .. "bolt_shut.wav")

View File

@@ -0,0 +1,375 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "SIG SG 550-1 Sniper"
SWEP.AbbrevName = "SG 550-1"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "1Elite"
SWEP.SubCatType = "6Marksman Rifle"
SWEP.Description = "Carbine caliber marksman rifle with fast automatic fire. Easy to control in short bursts and has high armor penetration. Equipped with a 6x scope by default."
SWEP.Description_Quote = "\"I work alone, like you. We always work alone.\"" -- The Bourne Identity (2002)
SWEP.Trivia_Caliber = "5.56x45mm"
SWEP.Trivia_Manufacturer = "SIG Sauer AG"
SWEP.Trivia_Year = "1988"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = [[
Model: Hav0c & Twinke Masta
Texture: Twinke Masta
Sound: Farion, Treyarch & Tactical Intervention
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_shark/v_sg550_sniper.mdl"
SWEP.WorldModel = "models/weapons/tacint_shark/w_sg550_sniper.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 25,
Damage_Min = 15,
RecoilKick = 3,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 22,
Damage_Min = 10,
RPM = 450,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.75
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 20,
Damage_Min = 12,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilSpreadPenalty = 0.005,
HipFireSpreadPenalty = 0.01,
RecoilDissipationRate = 8,
RecoilMaximum = 15
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.MarksmanRifle
SWEP.MuzzleVelocity = 28000
// "ballistics"
SWEP.Damage_Max = 28
SWEP.Damage_Min = 17
SWEP.Range_Min = 1800
SWEP.Range_Max = 4500
SWEP.Penetration = 10
SWEP.ArmorPenetration = 0.95
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 25000
// misc. shooting
SWEP.Firemodes = {
1,
2,
}
SWEP.RPM = 700
SWEP.RPMMultSemi = 0.8
SWEP.Spread = 0.0005
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 6
SWEP.RecoilResetTime = 0.07
SWEP.RecoilDissipationRate = 24
SWEP.RecoilFirstShotMult = 1
SWEP.RecoilVisualKick = 0.75
SWEP.RecoilKick = 3
SWEP.RecoilStability = 0.45
SWEP.RecoilAltMultiplier = 750
SWEP.RecoilSpreadPenalty = 0.0029
SWEP.HipFireSpreadPenalty = 0.06
SWEP.PeekPenaltyFraction = 0.15
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.85
SWEP.ShootingSpeedMult = 0.3
SWEP.SightedSpeedMult = 0.5
SWEP.ReloadSpeedMult = 0.4
SWEP.AimDownSightsTime = 0.42
SWEP.SprintToFireTime = 0.45
SWEP.Sway = 2
SWEP.ScopedSway = 0.1
SWEP.FreeAimMaxAngle = 7
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5.5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0, 0, 0)
SWEP.SightPos = Vector(-4.2, -7.5, -4.225)
SWEP.CorrectivePos = Vector(0, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// scope
SWEP.Scope = true
SWEP.ScopeOverlay = Material("tacrp/scopes/l96.png", "mips smooth") // Material("path/to/overlay")
SWEP.ScopeFOV = 90 / 6
SWEP.ScopeLevels = 1 // 2 = like CS:S
SWEP.ScopeHideWeapon = true
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 20
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/sg550.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.7
SWEP.DropMagazineTime = 0.6
// sounds
local path = "tacrp/weapons/sg551/sg551_"
local path1 = "tacint_shark/krieg/"
SWEP.Sound_Shoot = path1 .. "sg500.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 110
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["fire_iron"] = "dryfire",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.3, -0.2),
vm_ang = Angle(0, 0.5, 0),
t = 0.2,
tmax = 0.2,
bones = {
{
bone = "ValveBiped.bolt_cover",
pos = Vector(0, 0, -3),
t0 = 0.01,
t1 = 0.1,
},
},
}
// attachments
SWEP.AttachmentElements = {
["sights"] = {
BGs_VM = {
{1, 2}
},
BGs_WM = {
{2, 2}
},
},
["irons"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{2, 1}
},
},
["tactical"] = {
BGs_VM = {
{3, 1}
},
BGs_WM = {
{3, 1}
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"ironsights", "optic_cqb", "optic_medium", "optic_sniper"},
InstalledElements = {"sights"},
Bone = "ValveBiped.sg551_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.75,
WMScale = 0.75,
Pos_VM = Vector(-5.1, 0, 5.5),
Pos_WM = Vector(0, 5, 1),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.sg551_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
VMScale = 0.85,
Pos_VM = Vector(-3.2, 0.05, 32.25),
Pos_WM = Vector(0.1, 36, -1.2),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
InstalledElements = {"tactical"},
Bone = "ValveBiped.sg551_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
Pos_VM = Vector(-4.25, -0.75, 15),
Pos_WM = Vector(2, 13, -0.5),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(-90, -90 + 3.5, 0),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "perk_extendedmag", "acc_sling", "acc_duffle", "acc_bipod"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_krieg.Remove_Clip", path1 .. "magout.wav")
addsound("tacint_krieg.Insert_Clip", path1 .. "magin.ogg")
addsound("tacint_krieg.Insert_Clip-mid", path1 .. "magin.wav")
addsound("tacint_krieg.bolt_action", path1 .. "boltback.ogg")
addsound("tacint_krieg.bolt_slap", path1 .. "boltback.ogg")
addsound("tacint_krieg.bolt_back", path1 .. "boltback.ogg")
addsound("tacint_krieg.throw_catch", path .. "throw_catch.wav")
addsound("tacint_krieg.fire_selector", path .. "fire_selector.wav")

View File

@@ -0,0 +1,364 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "SIG SG 550-2 SP"
SWEP.AbbrevName = "SG 550-2"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "1Elite"
SWEP.SubCatType = "5Sporter"
SWEP.Description = "Long barrel rifle converted to semi-automatic for civilian markets. Easy to control and has high armor penetration."
SWEP.Description_Quote = "The Krieg 550 Commando's civilian brother."
SWEP.Trivia_Caliber = "5.56x45mm"
SWEP.Trivia_Manufacturer = "SIG Sauer AG"
SWEP.Trivia_Year = "1988"
SWEP.Faction = TacRP.FACTION_NEUTRAL
SWEP.Credits = [[
Model: Hav0c & Twinke Masta
Texture: Twinke Masta
Sound: Farion, Treyarch & Tactical Intervention
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_shark/v_sg550_rifle.mdl"
SWEP.WorldModel = "models/weapons/tacint_shark/w_sg550_rifle.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 30,
Damage_Min = 17,
HipFireSpreadPenalty = 0.05,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 22,
Damage_Min = 10,
RPM = 450,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.75
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 20,
Damage_Min = 12,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilSpreadPenalty = 0.005,
HipFireSpreadPenalty = 0.01,
RecoilDissipationRate = 8,
RecoilMaximum = 15
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.MarksmanRifle
SWEP.MuzzleVelocity = 26000
// "ballistics"
SWEP.Damage_Max = 30
SWEP.Damage_Min = 20
SWEP.Range_Min = 1800
SWEP.Range_Max = 4500
SWEP.Penetration = 10
SWEP.ArmorPenetration = 0.95
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 27000
// misc. shooting
SWEP.Firemodes = false
SWEP.Firemode = 1
SWEP.RPM = 500
SWEP.RPMMultSemi = 0.7
SWEP.Spread = 0.0008
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 6
SWEP.RecoilResetTime = 0.045
SWEP.RecoilDissipationRate = 22
SWEP.RecoilFirstShotMult = 0.8
SWEP.RecoilVisualKick = 1
SWEP.RecoilKick = 2.5
SWEP.RecoilStability = 0.55
SWEP.RecoilAltMultiplier = 200
SWEP.RecoilSpreadPenalty = 0.0033
SWEP.HipFireSpreadPenalty = 0.04
SWEP.PeekPenaltyFraction = 0.15
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.85
SWEP.ShootingSpeedMult = 0.8
SWEP.SightedSpeedMult = 0.5
SWEP.ReloadSpeedMult = 0.4
SWEP.AimDownSightsTime = 0.39
SWEP.SprintToFireTime = 0.44
SWEP.Sway = 2
SWEP.ScopedSway = 0.1
SWEP.FreeAimMaxAngle = 7
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5.5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0, 1, 0)
SWEP.SightPos = Vector(-4.17, -7.5, -4.425)
SWEP.CorrectivePos = Vector(0, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 20
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/sg550.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.7
SWEP.DropMagazineTime = 0.6
// sounds
local path = "tacrp/weapons/sg551/sg551_"
local path1 = "tacint_shark/krieg/"
SWEP.Sound_Shoot = path1 .. "sg500.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 110
SWEP.Pitch_Shoot = 94
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["fire_iron"] = "dryfire",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.3, -0.2),
vm_ang = Angle(0, 0.5, 0),
t = 0.2,
tmax = 0.2,
bones = {
{
bone = "ValveBiped.bolt_cover",
pos = Vector(0, 0, -3),
t0 = 0.01,
t1 = 0.1,
},
},
}
// attachments
SWEP.AttachmentElements = {
["sights"] = {
BGs_VM = {
{3, 2}
},
},
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
},
},
["tactical"] = {
BGs_VM = {
{2, 1}
},
BGs_WM = {
{2, 1}
},
},
}
SWEP.NoRMR = true
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium", "optic_sniper"},
InstalledElements = {"sights"},
Bone = "ValveBiped.sg551_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.75,
WMScale = 0.75,
Pos_VM = Vector(-5.1, 0, 6.0),
Pos_WM = Vector(0, 5, 1),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.sg551_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
VMScale = 0.85,
Pos_VM = Vector(-3.2, 0.05, 29.25),
Pos_WM = Vector(0.1, 33, -1.2),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
InstalledElements = {"tactical"},
Bone = "ValveBiped.sg551_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
Pos_VM = Vector(-4.25, -0.75, 15),
Pos_WM = Vector(2, 13, -0.5),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(-90, -90 + 3.5, 0),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock", "perk_extendedmag", "acc_sling", "acc_duffle", "acc_bipod"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_semi"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_krieg.Remove_Clip", path1 .. "magout.wav")
addsound("tacint_krieg.Insert_Clip", path1 .. "magin.ogg")
addsound("tacint_krieg.Insert_Clip-mid", path1 .. "magin.wav")
addsound("tacint_krieg.bolt_action", path1 .. "boltback.ogg")
addsound("tacint_krieg.bolt_slap", path1 .. "boltback.ogg")
addsound("tacint_krieg.bolt_back", path1 .. "boltback.ogg")
addsound("tacint_krieg.throw_catch", path .. "throw_catch.wav")
addsound("tacint_krieg.fire_selector", path .. "fire_selector.wav")

View File

@@ -0,0 +1,363 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "HK SL8"
SWEP.AbbrevName = "SL8"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "5Sporter"
SWEP.Description = "Semi-automatic variant of the G36 made for precision shooting. Low fire rate, but recoil control is excellent.\nEquipped with a 2x scope but has no ironsight option."
SWEP.Description_Quote = "\"Used to be a cop myself, only for one day though.\"" -- Resident Evil 4
SWEP.Trivia_Caliber = ".223 Remington"
SWEP.Trivia_Manufacturer = "Heckler & Koch"
SWEP.Trivia_Year = "1998"
SWEP.Faction = TacRP.FACTION_NEUTRAL
SWEP.Credits = [[
Model: Hav0c
Texture: Twinke Masta
Sound: KingFriday
Animation: Tactical Intervention
]]
// https://gamebanana.com/mods/211404
SWEP.ViewModel = "models/weapons/tacint_extras/v_sl8.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_sl8.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 28,
Damage_Min = 19,
Range_Min = 2000,
Range_Max = 8000,
ArmorPenetration = 0.875,
RPM = 360,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 35,
Damage_Min = 22,
Range_Min = 500,
Range_Max = 5000,
RPM = 200,
ClipSize = 25,
RecoilMaximum = 6,
RecoilResetTime = 0.2,
RecoilDissipationRate = 6,
RecoilSpreadPenalty = 0.002,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 17,
Damage_Min = 12,
Range_Min = 2000,
Range_Max = 8000,
ArmorPenetration = 0.875,
RPM = 360,
},
[TacRP.BALANCE_OLDSCHOOL] = {
HipFireSpreadPenalty = 0.015,
RecoilSpreadPenalty = 0.002
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 26
SWEP.Damage_Min = 16
SWEP.Range_Min = 1500
SWEP.Range_Max = 4000
SWEP.Penetration = 8 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.75
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 35000
// misc. shooting
SWEP.Firemode = 1
SWEP.RPM = 450
SWEP.RPMMultSemi = 0.7
SWEP.Spread = 0.001
SWEP.ShootTimeMult = 0.5
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 15
SWEP.RecoilResetTime = 0.175
SWEP.RecoilDissipationRate = 15
SWEP.RecoilFirstShotMult = 0.75
SWEP.RecoilVisualKick = 0.75
SWEP.RecoilKick = 1.5
SWEP.RecoilStability = 0.4
SWEP.RecoilAltMultiplier = 1000
SWEP.RecoilSpreadPenalty = 0.0009
SWEP.HipFireSpreadPenalty = 0.04
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.925
SWEP.ShootingSpeedMult = 0.85
SWEP.SightedSpeedMult = 0.6
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.4
SWEP.SprintToFireTime = 0.44
SWEP.Sway = 1.5
SWEP.ScopedSway = 0.1
SWEP.FreeAimMaxAngle = 6
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0.5, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(40, -15, 0)
SWEP.SprintPos = Vector(5, 0, -4)
SWEP.SightAng = Angle(0, 0, 0)
SWEP.SightPos = Vector(-4.03, -2.5, -4.1)
SWEP.CorrectivePos = Vector(0, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// scope
SWEP.Scope = true
SWEP.ScopeOverlay = Material("tacrp/scopes/g36.png", "mips smooth") // Material("path/to/overlay")
SWEP.ScopeFOV = 90 / 2
SWEP.ScopeLevels = 1 // 2 = like CS:S
SWEP.ScopeHideWeapon = true
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1.1
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/sl8.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.4
SWEP.DropMagazineTime = 0.4
// sounds
local path = "TacRP/weapons/g36k/g36k_"
local path1 = "tacint_extras/sl8/"
SWEP.Sound_Shoot = "^" .. path1 .. "sl8-1.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 120
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["fire_iron"] = "dryfire",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"},
["deploy"] = "deploy2",
}
SWEP.DeployTimeMult = 0.9
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -1, -0.1),
vm_ang = Angle(0, 0.4, 0),
t = 0.25,
tmax = 0.25,
}
// attachments
SWEP.AttachmentElements = {
["tactical"] = {
BGs_VM = {
{1, 1}
},
},
["irons"] = {
BGs_VM = {
{2, 1}
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium", "optic_sniper"},
Bone = "ValveBiped.g36k_rootbone",
WMBone = "Box01",
InstalledElements = {"irons"},
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
VMScale = 0.9,
Pos_VM = Vector(-6.8, 0, 7),
Pos_WM = Vector(0, 0, 2.75),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.g36k_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
Pos_VM = Vector(-3.55, 0.075, 32),
Pos_WM = Vector(-0.25, 24, -1),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.g36k_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
Pos_VM = Vector(-3.9, -0.75, 18),
Pos_WM = Vector(0.9, 20, -1),
Ang_VM = Angle(90, 0, -80),
Ang_WM = Angle(-70, -90, 0),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_sling", "acc_duffle", "perk_extendedmag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_semi"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_extras_sl8.MagOut", path1 .. "MagOut.wav")
addsound("tacint_extras_sl8.MagFiddle", path1 .. "MagFiddle.wav")
addsound("tacint_extras_sl8.MagSlap", path1 .. "MagSlap.wav")
addsound("tacint_extras_sl8.BoltPull", path1 .. "BoltPull.wav")
addsound("tacint_extras_sl8.BoltBack", path1 .. "BoltBack.wav")
addsound("tacint_extras_sl8.fire_select", path .. "fire_selector.wav")
addsound("tacint_extras_sl8.Buttstock_Back", path .. "buttstock_back.wav")

View File

@@ -0,0 +1,391 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Sako TRG-42"
SWEP.AbbrevName = "TRG-42"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "7Sniper Rifle"
SWEP.Description = "Magnum sniper rifle with decent handling and mobility.\nPowerful, but slow to cycle and not very stable.\nEquipped with a 12x scope by default."
SWEP.Description_Quote = "Almost unique in being a purpose-designed sharpshooter rifle." -- Hitman: Absolution (2012) (taken from the weapon description)
SWEP.Trivia_Caliber = ".338 Lapua Magnum"
SWEP.Trivia_Manufacturer = "SAKO"
SWEP.Trivia_Year = "1999"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = [[
Model: Darkstorn
Texture: SilentAssassin12
Sound: Vunsunta
Animation: Tactical Intervention
]]
// https://gamebanana.com/mods/211224
SWEP.ViewModel = "models/weapons/tacint_extras/v_trg42.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_trg42.mdl"
SWEP.Slot = 2
SWEP.SlotAlt = 3
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Description = "Magnum sniper rifle with decent handling and mobility.\nPowerful, but slow to fire and only lethal at long range.\nEquipped with a 12x scope by default.",
Damage_Max = 70,
Damage_Min = 115,
Range_Min = 1800,
Range_Max = 8000,
Sway = 2,
ScopedSway = 0.075,
},
[TacRP.BALANCE_TTT] = {
Description = "Magnum sniper rifle lethal to the chest at long range, but has poor handling and low close range damage.\nEquipped with a 12x scope by default.",
Damage_Max = 25,
Damage_Min = 80,
Range_Min = 1000,
Range_Max = 5000,
RPM = 30,
ShootTimeMult = 1.175,
ClipSize = 4,
AimDownSightsTime = 0.45,
RecoilResetTime = 0.4,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.75,
[HITGROUP_RIGHTARM] = 0.75,
[HITGROUP_LEFTLEG] = 0.5,
[HITGROUP_RIGHTLEG] = 0.5,
[HITGROUP_GEAR] = 0.5
},
},
[TacRP.BALANCE_PVE] = {
Description = "Magnum sniper rifle with decent handling and mobility.\nPowerful, but slow to fire and only lethal at long range.\nEquipped with a 12x scope by default.",
Damage_Max = 25,
Damage_Min = 75,
Range_Min = 700,
Range_Max = 3000,
Sway = 2,
ScopedSway = 0.075,
},
[TacRP.BALANCE_OLDSCHOOL] = {
HipFireSpreadPenalty = 0.023,
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.SniperRifle
// "ballistics"
SWEP.Damage_Max = 115
SWEP.Damage_Min = 90
SWEP.Range_Min = 1800
SWEP.Range_Max = 6000
SWEP.Penetration = 24 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.95
SWEP.ArmorBonus = 4
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.15,
[HITGROUP_LEFTARM] = 0.75,
[HITGROUP_RIGHTARM] = 0.75,
[HITGROUP_LEFTLEG] = 0.5,
[HITGROUP_RIGHTLEG] = 0.5,
[HITGROUP_GEAR] = 0.5
}
SWEP.MuzzleVelocity = 38000
// misc. shooting
SWEP.Firemode = 1
SWEP.FiremodeName = "Bolt-Action" // only used externally for firemode name distinction
SWEP.RPM = 32
SWEP.Spread = 0.00
SWEP.HipFireSpreadPenalty = 0.05
SWEP.PeekPenaltyFraction = 0.3
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 1
SWEP.RecoilResetTime = 0.3
SWEP.RecoilDissipationRate = 1
SWEP.RecoilFirstShotMult = 1 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 5
SWEP.RecoilKick = 6
SWEP.RecoilSpreadPenalty = 0 // extra spread per one unit of recoil
SWEP.CanBlindFire = true
SWEP.ShootTimeMult = 1.15
// handling
SWEP.MoveSpeedMult = 0.875
SWEP.ShootingSpeedMult = 0.65
SWEP.SightedSpeedMult = 0.5
SWEP.ReloadSpeedMult = 0.3
SWEP.AimDownSightsTime = 0.38
SWEP.SprintToFireTime = 0.46
SWEP.Sway = 2.25
SWEP.ScopedSway = 0.12
SWEP.FreeAimMaxAngle = 9
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.HoldTypeNPC = "shotgun"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_CROSSBOW
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_AR2
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(1.5, -2, -5.5)
SWEP.BlindFireAng = Angle(-10, -15, -0)
SWEP.BlindFirePos = Vector(3, -2, -2)
SWEP.BlindFireSuicideAng = Angle(0, 115, 0)
SWEP.BlindFireSuicidePos = Vector(0, 32, -24)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -4)
SWEP.SightAng = Angle(0.02, 0.11, 0)
SWEP.SightPos = Vector(-3.855, -11, -3.52)
SWEP.CorrectivePos = Vector(0.025, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK2
SWEP.HolsterPos = Vector(5, 8, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// scope
SWEP.Scope = true
SWEP.ScopeOverlay = Material("tacrp/scopes/sniper.png", "mips smooth") // Material("path/to/overlay")
SWEP.ScopeFOV = 90 / 12
SWEP.ScopeLevels = 1 // 2 = like CS:S
SWEP.ScopeHideWeapon = true
SWEP.ScopeOverlaySize = 0.75
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 5
SWEP.DefaultAmmo = 0
SWEP.Ammo = "357"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.Ammo_Expanded = "ti_sniper"
SWEP.ReloadTimeMult = 1.15
SWEP.DropMagazineImpact = "metal"
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/trg42.mdl"
SWEP.ReloadUpInTime = 1.75
SWEP.DropMagazineTime = 0.8
// sounds
local path = "TacRP/weapons/uratio/uratio_"
local path1 = "tacint_extras/trg42/"
SWEP.Sound_Shoot = "^" .. path1 .. "awp1.wav"
SWEP.Sound_Shoot_Silenced = "TacRP/weapons/ak47/ak47_fire_silenced-1.wav"
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_1"
SWEP.EjectEffect = 2
SWEP.EjectDelay = 0.9
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "draw",
["fire"] = {"shoot1", "shoot2"},
["blind_fire"] = "blind_shoot1"
}
// attachments
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
},
},
["optic"] = {
BGs_VM = {
{2, 1}
},
BGs_WM = {
{2, 1}
},
},
["irons"] = {
BGs_VM = {
{3, 1}
},
},
["muzzle"] = {
BGs_VM = {
{4, 1}
},
BGs_WM = {
{4, 1}
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"ironsights_sniper", "optic_cqb", "optic_medium", "optic_sniper"},
WMBone = "Box01",
Bone = "ValveBiped.uratio_rootbone",
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
InstalledElements = {"optic"},
VMScale = 0.8,
WMScale = 0.8,
Pos_VM = Vector(-5.1, 0.02, 6),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 6, 1.6),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
WMBone = "Box01",
Bone = "ValveBiped.uratio_rootbone",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
InstalledElements = {"muzzle"},
Pos_VM = Vector(-4.1, 0, 36.5),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 45, 0.5),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
WMBone = "Box01",
Bone = "ValveBiped.uratio_rootbone",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
Pos_VM = Vector(-2, 0, 17.5),
Ang_VM = Angle(90, 0, 180),
Pos_WM = Vector(0, 19.5, -2.6),
Ang_WM = Angle(0, -90, 180),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock", "acc_extmag_sniper", "acc_sling", "acc_duffle", "acc_bipod"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_manual"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_manual"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_sniper"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_extras_trg42.Clip_Out", path .. "clip_out.wav")
addsound("tacint_extras_trg42.Clip_In", path .. "clip_in.wav")
addsound("tacint_extras_trg42.Bolt_Back", path .. "bolt_back.wav")
addsound("tacint_extras_trg42.bolt_forward", path .. "bolt_forward.wav")
addsound("tacint_extras_trg42.safety", path .. "safety.wav")
addsound("tacint_extras_trg42.buttstock_back", path .. "buttstock_back.wav")
addsound("tacint_extras_trg42.buttstock_rest_down", path .. "buttstock_rest_down.wav")
addsound("tacint_extras_trg42.flip_up_cover", path .. "flip_up_cover.wav")

View File

@@ -0,0 +1,348 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "АС ВАЛ"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "4Assault Rifle"
SWEP.Description = "Integrally-suppressed rifle with high damage output and precision, but performs poorly over long bursts."
SWEP.Description_Quote = "\"Call me the cloaker-smoker!\"" -- PAYDAY 2 (2015)
SWEP.Trivia_Caliber = "9x39mm"
SWEP.Trivia_Manufacturer = "Tula Arms Plant"
SWEP.Trivia_Year = "1987"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = [[
Model & Texture: S.T.A.L.K.E.R.
Sound: S.T.A.L.K.E.R. & Vunsunta
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_extras/v_val.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_val.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 15,
Damage_Min = 12,
Range_Min = 800,
Range_Max = 4000,
RPM = 650,
RecoilSpreadPenalty = 0.005,
HipFireSpreadPenalty = 0.035,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4,
[HITGROUP_CHEST] = 1.5,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.8,
[HITGROUP_RIGHTARM] = 0.8,
[HITGROUP_LEFTLEG] = 0.6,
[HITGROUP_RIGHTLEG] = 0.6,
[HITGROUP_GEAR] = 0.6
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 10,
Damage_Min = 7,
Range_Min = 800,
Range_Max = 4000,
RPM = 800,
},
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 22
SWEP.Damage_Min = 16
SWEP.Range_Min = 900
SWEP.Range_Max = 2200
SWEP.Penetration = 9 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.925
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.85,
[HITGROUP_RIGHTLEG] = 0.85,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 14500
// misc. shooting
SWEP.Firemodes = {2, 1}
SWEP.RPM = 900
SWEP.Spread = 0.001
SWEP.ShootTimeMult = 0.5
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 5
SWEP.RecoilResetTime = 0.01
SWEP.RecoilDissipationRate = 28
SWEP.RecoilFirstShotMult = 0.75
SWEP.RecoilVisualKick = 0.75
SWEP.RecoilKick = 4.5
SWEP.RecoilStability = 0.45
SWEP.RecoilAltMultiplier = 300
SWEP.RecoilSpreadPenalty = 0.0035
SWEP.HipFireSpreadPenalty = 0.027
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.925
SWEP.ShootingSpeedMult = 0.75
SWEP.SightedSpeedMult = 0.55
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.39
SWEP.SprintToFireTime = 0.37
SWEP.Sway = 1.25
SWEP.ScopedSway = 0.175
SWEP.FreeAimMaxAngle = 5
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0.05, 0, 0)
SWEP.SightPos = Vector(-4.66, -7.5, -2.7)
SWEP.CorrectivePos = Vector(0, 0, -0.05)
SWEP.CorrectiveAng = Angle(0.75, 0.7, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, -2, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// scope
SWEP.Scope = true
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 20
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.Ammo_Expanded = "ti_pdw"
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/vss.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.65
SWEP.DropMagazineTime = 0.65
// sounds
local path = "tacint_extras/vss/"
SWEP.Sound_Shoot = "^" .. path .. "fire.wav"
SWEP.Sound_Shoot_Silenced = "^" .. path .. "fire.wav"
SWEP.Vol_Shoot = 80
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_suppressed"
SWEP.EjectEffect = 2
SWEP.Silencer = true
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "unholster",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"},
["jam"] = "mid_reload",
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.4, -0.1),
vm_ang = Angle(0, 0.1, 0),
t = 0.2,
tmax = 0.2,
bones = {
{
bone = "ValveBiped.bolt",
pos = Vector(0, 0, -3),
t0 = 0.01,
t1 = 0.15,
},
},
}
SWEP.DeployTimeMult = 2.2
SWEP.UnholsterTimeMult = 1 / 2.2
// attachments
SWEP.AttachmentElements = {
["tactical"] = {
BGs_VM = {
{2, 1}
},
BGs_WM = {
{2, 1}
},
},
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
},
},
["pso1"] = {
BGs_VM = {
{2, 2}
},
BGs_WM = {
{2, 2}
},
},
["akmount"] = {
BGs_VM = {
{2, 0}
},
BGs_WM = {
{2, 0}
},
AttPosMods = {
[1] = {
Pos_VM = Vector(-5.5, 0.5, 2.5),
Pos_WM = Vector(-0.4, 2, 0.5),
}
},
SortOrder = 2,
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_pso1", "optic_cqb", "optic_medium", "optic_sniper", "optic_ak2"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
InstalledElements = {"tactical"},
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.75,
Pos_VM = Vector(-5.25, 0.15, 4),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 3, 0.2),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
Pos_VM = Vector(-3.25, -0.1, 19),
Pos_WM = Vector(0, 19, -2),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, -90, 180),
},
[3] = {
PrintName = "Accessory",
Category = {"acc_foldstock", "acc", "acc_sling", "acc_duffle", "perk_extendedmag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[4] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Ammo",
Category = {"ammo_rifle_sub"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}

View File

@@ -0,0 +1,368 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "ВСС Винторез"
SWEP.AbbrevName = "Vintorez"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "6Marksman Rifle"
SWEP.Description = "Integrally-suppressed marksman rifle with high fire rate and low recoil, but performs poorly over long bursts.\nEquipped with a 6x scope by default."
SWEP.Description_Quote = "\"Enemy has no more medicine!\"" -- PAYDAY 2 (2015)
SWEP.Trivia_Caliber = "9x39mm"
SWEP.Trivia_Manufacturer = "Tula Arms Plant"
SWEP.Trivia_Year = "1987"
SWEP.Faction = TacRP.FACTION_MILITIA
SWEP.Credits = [[
Model: Ettubrutesbro, Millenia & Twinke Masta
Texture: Millenia
Sound: S.T.A.L.K.E.R. & Vunsunta
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_extras/v_vss.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_vss.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 15,
Damage_Min = 12,
Range_Min = 800,
Range_Max = 4000,
RPM = 650,
RecoilSpreadPenalty = 0.005,
HipFireSpreadPenalty = 0.035,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4,
[HITGROUP_CHEST] = 1.5,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.8,
[HITGROUP_RIGHTARM] = 0.8,
[HITGROUP_LEFTLEG] = 0.6,
[HITGROUP_RIGHTLEG] = 0.6,
[HITGROUP_GEAR] = 0.6
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 13,
Damage_Min = 8,
Range_Min = 1000,
Range_Max = 5000,
RPM = 600,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilSpreadPenalty = 0.004
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 24
SWEP.Damage_Min = 20
SWEP.Range_Min = 1000
SWEP.Range_Max = 2500
SWEP.Penetration = 9 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.925
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.85,
[HITGROUP_RIGHTLEG] = 0.85,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 16000
// misc. shooting
SWEP.Firemodes = {
1,
2
}
SWEP.RPM = 700
SWEP.Spread = 0.0005
SWEP.ShootTimeMult = 0.5
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 5
SWEP.RecoilResetTime = 0.01
SWEP.RecoilDissipationRate = 28
SWEP.RecoilFirstShotMult = 0.65
SWEP.RecoilVisualKick = 0.5
SWEP.RecoilKick = 3
SWEP.RecoilStability = 0.5
SWEP.RecoilAltMultiplier = 400
SWEP.RecoilSpreadPenalty = 0.0048
SWEP.HipFireSpreadPenalty = 0.03
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.925
SWEP.ShootingSpeedMult = 0.75
SWEP.SightedSpeedMult = 0.55
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.44
SWEP.SprintToFireTime = 0.4
SWEP.Sway = 1.3
SWEP.ScopedSway = 0.1
SWEP.FreeAimMaxAngle = 5.5
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0.05, 0, 0)
SWEP.SightPos = Vector(-4.66, -7.5, -2.7)
SWEP.CorrectivePos = Vector(0, 0, -0.05)
SWEP.CorrectiveAng = Angle(0.75, 0.7, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, -2, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// scope
SWEP.Scope = true
SWEP.ScopeOverlay = Material("tacrp/scopes/pso1.png", "mips smooth") // Material("path/to/overlay")
SWEP.ScopeFOV = 90 / 6
SWEP.ScopeLevels = 1
SWEP.ScopeHideWeapon = true
SWEP.ScopeOverlaySize = 0.9
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 20
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.Ammo_Expanded = "ti_pdw"
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/vss.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.65
SWEP.DropMagazineTime = 0.65
// sounds
local path = "tacint_extras/vss/"
local path1 = "tacrp_extras/ak47/"
SWEP.Sound_Shoot = "^" .. path .. "fire.wav"
SWEP.Sound_Shoot_Silenced = "^" .. path .. "fire.wav"
SWEP.Vol_Shoot = 80
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_suppressed"
SWEP.EjectEffect = 2
SWEP.Silencer = true
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "unholster",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"},
["jam"] = "mid_reload",
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.4, -0.1),
vm_ang = Angle(0, 0.1, 0),
t = 0.2,
tmax = 0.2,
bones = {
{
bone = "ValveBiped.bolt",
pos = Vector(0, 0, -3),
t0 = 0.01,
t1 = 0.15,
},
},
}
SWEP.DeployTimeMult = 2.25
// attachments
SWEP.AttachmentElements = {
["tactical"] = {
BGs_VM = {
{2, 1}
},
BGs_WM = {
{2, 1}
},
},
["irons"] = {
BGs_VM = {
{2, 2}
},
BGs_WM = {
{2, 2}
},
},
["akmount"] = {
BGs_VM = {
{2, 2}
},
BGs_WM = {
{2, 2}
},
AttPosMods = {
[1] = {
Pos_VM = Vector(-5.5, 0.5, 2.5),
Pos_WM = Vector(-0.4, 2, 0.5),
}
},
SortOrder = 2,
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"ironsights", "optic_cqb", "optic_medium", "optic_sniper", "optic_ak2"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
InstalledElements = {"tactical"},
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
VMScale = 0.75,
Pos_VM = Vector(-5.25, 0.15, 4),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 3, 0.2),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.AK47_rootbone",
WMBone = "Box01",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
Pos_VM = Vector(-3.25, -0.1, 19),
Pos_WM = Vector(0, 19, -2),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, -90, 180),
},
[3] = {
PrintName = "Accessory",
Category = {"acc", "acc_sling", "acc_duffle", "perk_extendedmag", "acc_bipod"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[4] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Ammo",
Category = {"ammo_rifle_sub"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_extras_vss.remove_clip", path .. "clipin1.wav")
addsound("tacint_extras_vss.insert_clip", path .. "clipin2.wav")
addsound("tacint_extras_vss.boltaction", path1 .. "bolt.mp3")
addsound("tacint_extras_vss.Buttstock_Back", path .. "buttstock_back.wav")

View File

@@ -0,0 +1,333 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "HK XM8 Compact"
SWEP.AbbrevName = "XM8 Compact"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "4Assault Rifle"
SWEP.Description = "Experimental multi-purpose carbine. Easy to use, but low damage.\nHas an adjustable integrated 2-8x scope."
SWEP.Description_Quote = "\"Who loves spaghetti?!\"" -- Battlefield: Bad Company 2
SWEP.Trivia_Caliber = "5.56x45mm"
SWEP.Trivia_Manufacturer = "Heckler & Koch"
SWEP.Trivia_Year = "2003"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = [[
Model: End Of Days
Texture: Copkiller, Twinke Masta & Wangchung
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_shark/v_xm8car.mdl"
SWEP.WorldModel = "models/weapons/tacint_shark/w_xm8car.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 12,
Damage_Min = 6,
Range_Min = 750,
Range_Max = 2500,
RPM = 750,
RecoilSpreadPenalty = 0.001,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 10,
Damage_Min = 7,
RPM = 700,
},
[TacRP.BALANCE_OLDSCHOOL] = {
HipFireSpreadPenalty = 0.022,
RecoilMaximum = 15
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 18
SWEP.Damage_Min = 10
SWEP.Range_Min = 1000
SWEP.Range_Max = 2500
SWEP.Penetration = 7 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.7
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 29000
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 750
SWEP.Spread = 0.0025
SWEP.ShootTimeMult = 0.5
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 12
SWEP.RecoilResetTime = 0.1 // time after you stop shooting for recoil to start dissipating
SWEP.RecoilDissipationRate = 20
SWEP.RecoilFirstShotMult = 1 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 0.5
SWEP.RecoilKick = 1.5
SWEP.RecoilStability = 0.5
SWEP.RecoilSpreadPenalty = 0.001
SWEP.HipFireSpreadPenalty = 0.025
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.95
SWEP.ShootingSpeedMult = 0.9
SWEP.SightedSpeedMult = 0.85
SWEP.ReloadSpeedMult = 0.75
SWEP.AimDownSightsTime = 0.33
SWEP.SprintToFireTime = 0.35
SWEP.Sway = 1.25
SWEP.ScopedSway = 0.15
SWEP.FreeAimMaxAngle = 3
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(40, -15, 0)
SWEP.SprintPos = Vector(5, 0, -4)
SWEP.SightAng = Angle(0, 0, 0)
SWEP.SightPos = Vector(-4.03, -2.5, -4.1)
SWEP.CorrectivePos = Vector(0, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// scope
SWEP.Scope = true
SWEP.ScopeOverlay = Material("tacrp/scopes/scopeddot.png", "mips smooth") // Material("path/to/overlay")
SWEP.ScopeFOV = 90 / 2
SWEP.ScopeLevels = 1 // 2 = like CS:S
SWEP.ScopeHideWeapon = true
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/xm8.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.3
SWEP.DropMagazineTime = 0.4
// sounds
local path = "tacrp/weapons/g36k/g36k_"
local path1 = "tacint_extras/xm8/"
SWEP.Sound_Shoot = "^" .. path1 .. "m249-1.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 120
SWEP.Pitch_Shoot = 105
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "unholster",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
SWEP.DeployTimeMult = 1.75
// attachments
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
}
},
["tactical"] = {
BGs_VM = {
{2, 1}
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_xm8"},
AttachSound = "tacrp/weapons/mp5/mp5_fire_select-1.wav",
DetachSound = "tacrp/weapons/mp5/mp5_fire_select-3.wav",
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.g36k_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
Pos_VM = Vector(-3.3, 0.075, 22),
Pos_WM = Vector(-0.25, 24, -1),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.g36k_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
VMScale = 1.1,
Pos_VM = Vector(-4.4, -0.3, 14.2),
Pos_WM = Vector(0.9, 15, -1),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(-70, -90, 0),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock2", "acc_sling", "acc_duffle", "perk_extendedmag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_xm8c.remove_clip", path .. "remove_clip.wav")
addsound("tacint_xm8c.insert_clip", path .. "insert_clip.wav")
addsound("tacint_xm8c.bolt_action", path .. "bolt_action.wav")
addsound("tacint_xm8c.fire_select", path .. "fire_selector.wav")
addsound("tacint_xm8c.Buttstock_Back", path .. "buttstock_back.wav")

View File

@@ -0,0 +1,346 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "HK XM8 LMG"
SWEP.AbbrevName = "XM8 LMG"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "5Machine Gun"
SWEP.Description = "Experimental multi-purpose carbine in MG configuration. Light, high capacity and low recoil, but damage is poor.\nHas an adjustable integrated 2-8x scope."
SWEP.Description_Quote = "\"How ya like me now, bitch!?\"" -- Battlefield: Bad Company 2
SWEP.Trivia_Caliber = "5.56x45mm"
SWEP.Trivia_Manufacturer = "Heckler & Koch"
SWEP.Trivia_Year = "2003"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = [[
Model: End Of Days
Texture: Copkiller, Twinke Masta & Wangchung
Animation: Tactical Intervention
]]
SWEP.ViewModel = "models/weapons/tacint_extras/v_xm8lmg.mdl"
SWEP.WorldModel = "models/weapons/tacint_extras/w_xm8lmg.mdl"
SWEP.Slot = 2
SWEP.SlotAlt = 3
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 12,
Damage_Min = 6,
Range_Min = 750,
Range_Max = 3000,
RPM = 750,
RecoilSpreadPenalty = 0.0009,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 10,
Damage_Min = 7,
RPM = 700,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilSpreadPenalty = 0.001,
HipFireSpreadPenalty = 0.01,
RecoilMaximum = 14
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.MachineGun
// "ballistics"
SWEP.Damage_Max = 18
SWEP.Damage_Min = 10
SWEP.Range_Min = 1200
SWEP.Range_Max = 3000
SWEP.Penetration = 7 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.7
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 32000
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 750
SWEP.Spread = 0.008
SWEP.ShootTimeMult = 0.5
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 25
SWEP.RecoilResetTime = 0.1 // time after you stop shooting for recoil to start dissipating
SWEP.RecoilDissipationRate = 20
SWEP.RecoilFirstShotMult = 1 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 0.5
SWEP.RecoilKick = 2
SWEP.RecoilStability = 0.5
SWEP.RecoilSpreadPenalty = 0.0007
SWEP.HipFireSpreadPenalty = 0.035
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.9
SWEP.ShootingSpeedMult = 0.75
SWEP.SightedSpeedMult = 0.75
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.42
SWEP.SprintToFireTime = 0.37
SWEP.Sway = 1
SWEP.ScopedSway = 0.225
SWEP.FreeAimMaxAngle = 4.5
SWEP.Bipod = true
SWEP.BipodRecoil = 0.65
SWEP.BipodKick = 0.3
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(40, -15, 0)
SWEP.SprintPos = Vector(5, 0, -4)
SWEP.SightAng = Angle(0, 0, 0)
SWEP.SightPos = Vector(-4.03, -2.5, -4.1)
SWEP.CorrectivePos = Vector(0, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// scope
SWEP.Scope = true
SWEP.ScopeOverlay = Material("tacrp/scopes/scopeddot.png", "mips smooth") // Material("path/to/overlay")
SWEP.ScopeFOV = 90 / 2
SWEP.ScopeLevels = 1 // 2 = like CS:S
SWEP.ScopeHideWeapon = true
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 100
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1.5
SWEP.DropMagazineModel = "models/weapons/tacint_extras/magazines/xm8lmg.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.4
SWEP.DropMagazineTime = 0.4
// sounds
local path = "tacrp/weapons/g36k/g36k_"
local path1 = "tacint_extras/xm8/"
SWEP.Sound_Shoot = "^" .. path1 .. "m249-1.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 120
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "unholster",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
SWEP.DeployTimeMult = 2.25
// attachments
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
}
},
["tactical"] = {
BGs_VM = {
{2, 1}
},
},
["bipod"] = {
BGs_VM = {
{3, 1}
},
BGs_WM = {
{3, 1}
}
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_xm8"},
AttachSound = "tacrp/weapons/mp5/mp5_fire_select-1.wav",
DetachSound = "tacrp/weapons/mp5/mp5_fire_select-3.wav",
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.g36k_rootbone",
WMBone = "ValveBiped.Bip01_R_Hand",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
WMScale = 0.9,
Pos_VM = Vector(-3.65, 0.3, 31),
Pos_WM = Vector(35, 1.2, -4.7),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -0, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.g36k_rootbone",
WMBone = "ValveBiped.Bip01_R_Hand",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
Pos_VM = Vector(-3.75, -0.8, 17),
Pos_WM = Vector(20, 2, -5),
Ang_VM = Angle(90, 0, -80),
Ang_WM = Angle(-0, 0, 90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock2", "acc_sling", "acc_duffle", "extendedbelt", "acc_bipod"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_xm8.remove_clip", path1 .. "magout.wav")
addsound("tacint_xm8.insert_clip", path1 .. "magin.wav")
addsound("tacint_xm8.bolt_action", path .. "bolt_action.wav")
addsound("tacint_xm8.fire_select", path .. "fire_selector.wav")
addsound("tacint_xm8.Buttstock_Back", path .. "buttstock_back.wav")

View File

@@ -0,0 +1,100 @@
SWEP.Base = "tacrp_base_knife"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Flip Knife"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.SubCatTier = "9Special"
SWEP.SubCatType = "8Bladed Melee"
SWEP.Description = "A multi-purpose flip knife, although most of the purposes involving stabbing someone."
SWEP.Description_Quote = "Stabbin' time."
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_knife.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_knife.mdl"
SWEP.Slot = 0
SWEP.MeleeDamage = 35
SWEP.MeleeAttackTime = 0.4
SWEP.MeleeAttackMissTime = 0.5
SWEP.MeleeDelay = 0.15
SWEP.MeleeDamageType = DMG_SLASH
SWEP.MeleePerkStr = 0.5
SWEP.MeleePerkAgi = 0.5
SWEP.MeleePerkInt = 0.5
// hold types
SWEP.HoldType = "knife"
SWEP.HoldTypeSprint = "knife"
SWEP.GestureBash = ACT_HL2MP_GESTURE_RANGE_ATTACK_KNIFE
SWEP.GestureBash2 = ACT_HL2MP_GESTURE_RANGE_ATTACK_MELEE
SWEP.PassiveAng = Angle(-2.5, 0, 0)
SWEP.PassivePos = Vector(1, 0, -5)
SWEP.SprintAng = Angle(0, 0, 0)
SWEP.SprintPos = Vector(2, 0, -5)
SWEP.CustomizeAng = Angle(0, 25, 0)
SWEP.CustomizePos = Vector(2, 0, -12)
SWEP.SprintMidPoint = {
Pos = Vector(2, 0, -5),
Ang = Angle(0, 0, 0)
}
// sounds
local path = "tacrp/weapons/knife/"
SWEP.AnimationTranslationTable = {
["deploy"] = "deploy",
["melee"] = {"slash_left1", "slash_left2", "slash_right1", "slash_right2"},
["melee2"] = {"slash_forward1", "slash_forward2"},
["meleethrow"] = {"knifethrow"},
}
SWEP.Sound_MeleeHit = {
path .. "/scrape_metal-1.wav",
path .. "/scrape_metal-2.wav",
path .. "/scrape_metal-3.wav",
}
SWEP.Sound_MeleeHitBody = {
path .. "/flesh_hit-1.wav",
path .. "/flesh_hit-2.wav",
path .. "/flesh_hit-3.wav",
path .. "/flesh_hit-4.wav",
path .. "/flesh_hit-5.wav",
}
SWEP.Sound_MeleeSwing = {
path .. "swing-1.wav",
path .. "swing-2.wav",
path .. "swing-3.wav",
path .. "swing-4.wav",
path .. "swing-5.wav",
path .. "swing-6.wav",
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_knife.deploy", path .. "open-1.wav")

View File

@@ -0,0 +1,102 @@
SWEP.Base = "tacrp_base_knife"
SWEP.Spawnable = true
AddCSLuaFile()
SWEP.PrintName = "Jackal Knife"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.SubCatTier = "9Special"
SWEP.SubCatType = "8Bladed Melee"
SWEP.Description = "Very edgy looking knife. Light, partially skeletized blade makes it faster to swing but do less damage."
SWEP.Description_Quote = "That doesn't look very pleasant."
SWEP.Faction = TacRP.FACTION_MILITIA
SWEP.Credits = "Assets: Tactical Intervention (unused)"
SWEP.ViewModel = "models/weapons/tacint/v_knife2.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_knife2.mdl"
SWEP.NoRanger = true
SWEP.NoStatBox = false
SWEP.Slot = 0
SWEP.MeleeDamage = 30
SWEP.MeleeAttackTime = 0.35
SWEP.MeleeAttackMissTime = 0.45
SWEP.MeleeDelay = 0.12
SWEP.MeleeDamageType = DMG_SLASH
SWEP.MeleePerkStr = 0.5
SWEP.MeleePerkAgi = 0.6
SWEP.MeleePerkInt = 0.55
// hold types
SWEP.HoldType = "knife"
SWEP.HoldTypeSprint = "knife"
SWEP.GestureBash = ACT_HL2MP_GESTURE_RANGE_ATTACK_KNIFE
SWEP.GestureBash2 = ACT_HL2MP_GESTURE_RANGE_ATTACK_MELEE
SWEP.PassiveAng = Angle(-2.5, 0, 0)
SWEP.PassivePos = Vector(1, 0, -5)
SWEP.SprintAng = Angle(0, 0, 0)
SWEP.SprintPos = Vector(2, 0, -5)
SWEP.CustomizeAng = Angle(0, 25, 0)
SWEP.CustomizePos = Vector(2, 0, -12)
SWEP.SprintMidPoint = {
Pos = Vector(2, 0, -5),
Ang = Angle(0, 0, 0)
}
// sounds
local path = "tacrp/weapons/knife/"
SWEP.AnimationTranslationTable = {
["deploy"] = "deploy",
["melee"] = {"slash_left1", "slash_left2", "slash_right1", "slash_right2"},
["melee2"] = {"slash_forward1", "slash_forward2"},
["meleethrow"] = {"knifethrow"},
}
SWEP.Sound_MeleeHit = {
path .. "/scrape_metal-1.wav",
path .. "/scrape_metal-2.wav",
path .. "/scrape_metal-3.wav",
}
SWEP.Sound_MeleeHitBody = {
path .. "/flesh_hit-1.wav",
path .. "/flesh_hit-2.wav",
path .. "/flesh_hit-3.wav",
path .. "/flesh_hit-4.wav",
path .. "/flesh_hit-5.wav",
}
SWEP.Sound_MeleeSwing = {
path .. "swing-1.wav",
path .. "swing-2.wav",
path .. "swing-3.wav",
path .. "swing-4.wav",
path .. "swing-5.wav",
path .. "swing-6.wav",
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_knife2.deploy", "tacrp/magtap.ogg")

View File

@@ -0,0 +1,315 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "KC-23"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "1Elite"
SWEP.SubCatType = "5Shotgun"
SWEP.Description = "Massive shotgun that shoots massive shells from its massive barrel.\nAble to breach doors without specialized shells."
SWEP.Description_Quote = "\"You tried to make me kill my president!\" \"Tried?\"" -- Black Ops 1 (2010)
SWEP.Trivia_Caliber = "23x75mmR"
SWEP.Trivia_Manufacturer = "Tula Arms Plant"
SWEP.Trivia_Year = "1971"
SWEP.Faction = TacRP.FACTION_MILITIA
SWEP.Credits = "Assets: Firearms: Source"
SWEP.ViewModel = "models/weapons/tacint/v_ks23.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_ks23.mdl"
SWEP.Slot = 2
SWEP.SlotAlt = 3
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 10,
Damage_Min = 2,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 8,
Damage_Min = 2,
Range_Min = 100,
Range_Max = 1000,
Num = 16,
ClipSize = 4,
Spread = 0.04,
ShotgunPelletSpread = 0.03,
HipFireSpreadPenalty = 0.025,
RecoilSpreadPenalty = 0.02,
FreeAimMaxAngle = 5,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 9,
Damage_Min = 4,
Range_Min = 500,
Range_Max = 3000,
Num = 32,
Spread = 0.06,
ShotgunPelletSpread = 0.015,
},
[TacRP.BALANCE_OLDSCHOOL] = {
HipFireSpreadPenalty = 0.04,
RecoilDissipationRate = 1.25,
RecoilMaximum = 5,
ReloadTimeMult = 1.3
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.Shotgun
// "ballistics"
SWEP.Damage_Max = 14
SWEP.Damage_Min = 4
SWEP.Range_Min = 100 // distance for which to maintain maximum damage
SWEP.Range_Max = 1200 // distance at which we drop to minimum damage
SWEP.Penetration = 4 // units of metal this weapon can penetrate
SWEP.Num = 20
SWEP.ArmorPenetration = 0.35
SWEP.ArmorBonus = 0.25
SWEP.MuzzleVelocity = 10000
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 1,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 1,
[HITGROUP_RIGHTLEG] = 1,
[HITGROUP_GEAR] = 1
}
// misc. shooting
SWEP.Firemode = 1
SWEP.FiremodeName = "Pump-Action" // only used externally for firemode name distinction
SWEP.RPM = 45
SWEP.Spread = 0.04
SWEP.ShotgunPelletSpread = 0.035
SWEP.ShootTimeMult = 1
SWEP.HipFireSpreadPenalty = 0.025
SWEP.MidAirSpreadPenalty = 0
SWEP.ScopedSpreadPenalty = 0
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 3
SWEP.RecoilResetTime = 0.35
SWEP.RecoilDissipationRate = 1
SWEP.RecoilFirstShotMult = 1.5
SWEP.RecoilVisualKick = 2
SWEP.RecoilKick = 25
SWEP.RecoilStability = 0.65
SWEP.RecoilSpreadPenalty = 0.02
SWEP.CanBlindFire = true
SWEP.DoorBreach = true
SWEP.DoorBreachThreshold = 100
// handling
SWEP.MoveSpeedMult = 0.85
SWEP.ShootingSpeedMult = 0.5
SWEP.SightedSpeedMult = 0.6
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.37
SWEP.SprintToFireTime = 0.4
SWEP.Sway = 1.5
SWEP.ScopedSway = 0.65
SWEP.FreeAimMaxAngle = 4
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.HoldTypeNPC = "shotgun"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_SHOTGUN
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SHOTGUN
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(4, -2, -4)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(-0.55, 0.1, 0.75)
SWEP.SightPos = Vector(-3.4, -2, -3.25)
SWEP.CorrectivePos = Vector(0.275, 0, -0.2)
SWEP.CorrectiveAng = Angle(1.21, 0.1, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK2
SWEP.HolsterPos = Vector(5, 8, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 4
SWEP.DefaultAmmo = 0
SWEP.Ammo = "buckshot"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ShotgunReload = true
SWEP.ReloadTimeMult = 1.25
SWEP.ShotgunThreeload = false
// sounds
local path = "TacRP/weapons/ks23/ks23_"
SWEP.Sound_Shoot = "tacrp/weapons/ks23/ks23_fire1.wav"
SWEP.Sound_Shoot_Silenced = "TacRP/weapons/sg551/sg551_fire_silenced-1.wav"
SWEP.Vol_Shoot = 130
SWEP.Pitch_Shoot = 95
SWEP.ShootPitchVariance = 0 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_shotgun"
SWEP.EjectEffect = 4
SWEP.EjectDelay = 0.5
// anims
SWEP.AnimationTranslationTable = {
["fire"] = {"shoot1", "shoot2"},
["blind_fire"] = {"blind_shoot1"},
["melee"] = {"melee1", "melee2"},
["reload"] = {"reload", "reload2"},
["jam"] = "reload_finish"
}
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium"},
Bone = "ValveBiped.bekas_rootbone",
WMBone = "ValveBiped.Bip01_R_Hand",
InstalledElements = {"sights"},
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
VMScale = 0.75,
Pos_VM = Vector(-3.4, 0, 8),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(9, 0.85, -7),
Ang_WM = Angle(-25, 3.5, 180),
},
[2] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom"},
Bone = "ValveBiped.bekas_rootbone",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
VMScale = 1.15,
Pos_VM = Vector(-2, -0.3, 22),
Ang_VM = Angle(90, 0, -90),
Pos_WM = Vector(22, 0.5, -11),
Ang_WM = Angle(-25, 3.5, 90),
},
[3] = {
PrintName = "Accessory",
Category = {"acc", "acc_duffle", "acc_extmag_shotgun_tube", "acc_sling"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[4] = {
PrintName = "Bolt",
Category = {"bolt_manual"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Trigger",
Category = {"trigger_manual", "trigger_pump"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Ammo",
Category = {"ammo_shotgun", "ammo_ks23"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_ks23.Insertshell", "tacrp/weapons/bekas/insertshell-1.wav")
addsound("tacint_ks23.Movement", "tacrp/weapons/bekas/movement-1.wav")
addsound("tacint_ks23.PumpBack", path .. "pump_back.wav")
addsound("tacint_ks23.PumpForward", path .. "pump_forward.wav")

View File

@@ -0,0 +1,264 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "HK M320"
SWEP.AbbrevName = "M320"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.NoAimAssist = true
SWEP.SubCatTier = "9Special"
SWEP.SubCatType = "6Launcher"
SWEP.Description = "Grenade launcher capable of firing a variety of payloads."
SWEP.Description_Quote = "Not beanbags, NOT BEANBAGS!"
SWEP.Trivia_Caliber = "40mm Grenades"
SWEP.Trivia_Manufacturer = "Heckler & Koch"
SWEP.Trivia_Year = "2008"
SWEP.Faction = TacRP.FACTION_NEUTRAL
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_m320.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_m320.mdl"
SWEP.NoRanger = true
SWEP.Slot = 4
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
},
}
// "ballistics"
SWEP.Damage_Max = 150
SWEP.Damage_Min = 150
SWEP.Range_Max = 4000
SWEP.Range_Min = 1000
SWEP.ShootEnt = "tacrp_proj_40mm_he"
SWEP.ShootEntForce = 4000
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 1,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 7000
SWEP.Num = 1
// misc. shooting
SWEP.Firemode = 1
SWEP.FiremodeName = "Single-Shot" // only used externally for firemode name distinction
SWEP.RPM = 60
SWEP.Spread = 0.025
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 1
SWEP.RecoilResetTime = 0.2 // time after you stop shooting for recoil to start dissipating
SWEP.RecoilDissipationRate = 1
SWEP.RecoilFirstShotMult = 1 // multiplier for the first shot's recoil amount
SWEP.RecoilVisualKick = 5
SWEP.RecoilVisualShake = 2
SWEP.RecoilKick = 15
SWEP.RecoilSpreadPenalty = 0 // extra spread per one unit of recoil
SWEP.HipFireSpreadPenalty = 0.05
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.9
SWEP.ShootingSpeedMult = 0.5
SWEP.SightedSpeedMult = 0.7
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.25
SWEP.SprintToFireTime = 0.32 // multiplies how long it takes to recover from sprinting
SWEP.Sway = 1
SWEP.ScopedSway = 0.2
SWEP.FreeAimMaxAngle = 6
// hold types
SWEP.HoldType = "smg"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_RPG
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_AR2
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(2, -2, -6)
SWEP.BlindFireAng = Angle(0, 0, -30)
SWEP.BlindFirePos = Vector(1, -3, 0)
SWEP.BlindFireLeftAng = Angle(75, 0, 0)
SWEP.BlindFireLeftPos = Vector(8, 10, -6)
SWEP.BlindFireSuicideAng = Angle(0, 135, 0)
SWEP.BlindFireSuicidePos = Vector(-3, 25, -19)
SWEP.SprintAng = Angle(40, -15, 0)
SWEP.SprintPos = Vector(4, 0, -4)
SWEP.SightAng = Angle(1.075, 7.1, 0)
SWEP.SightPos = Vector(-1.34, 0, -8.15)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_GEAR
SWEP.HolsterPos = Vector(0, -2, -3)
SWEP.HolsterAng = Angle(0, -90, -25)
// melee
SWEP.CanMeleeAttack = true
// reload
SWEP.ClipSize = 1
SWEP.Ammo = "smg1_grenade"
// sounds
local path = "TacRP/weapons/m320/"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_m79"
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "draw",
["blind_idle"] = "idle",
["blind_fire"] = "fire",
}
// attachments
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
}
},
["3gl"] = {
BGs_VM = {
{2, 1}
},
},
["buck"] = {
BGs_VM = {
{2, 2}
},
},
["heat"] = {
BGs_VM = {
{2, 3}
},
},
["lvg"] = {
BGs_VM = {
{2, 4}
},
},
["smoke"] = {
BGs_VM = {
{2, 5}
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Ammo",
Category = "ammo_40mm",
AttachSound = "TacRP/weapons/m320/shell_in-1.wav",
DetachSound = "TacRP/weapons/m320/shell_out-1.wav",
},
[2] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock2", "acc_holster"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[3] = {
PrintName = "Perk",
Category = {"perk", "perk_shooting", "perk_reload", "perk_melee"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("TacInt_m320.Tube_Open", path .. "tube_open-1.wav")
addsound("TacInt_m320.Tube_close", path .. "tube_close-1.wav")
addsound("TacInt_m320.shell_out", path .. "shell_out-1.wav")
addsound("TacInt_m320.shell_in", path .. "shell_in-1.wav")
addsound("TacInt_m320.buttstock_back", path .. "buttstock_back-1.wav")
addsound("TacInt_m320.sight_flipup", path .. "sight_flipup-1.wav")
SWEP.AutoSpawnable = false
if engine.ActiveGamemode() == "terrortown" then
SWEP.AutoSpawnable = false
SWEP.Kind = WEAPON_EQUIP
SWEP.Slot = 6
SWEP.CanBuy = { ROLE_TRAITOR }
SWEP.EquipMenuData = {
type = "Weapon",
desc = "Low power grenade launcher. Variety of payload\noptions, but standard explosive grenades are weak.\nComes with 3 grenades.\n\nBEWARE: May be visible while holstered!",
}
function SWEP:TTTBought(buyer)
buyer:GiveAmmo(2, "SMG1_Grenade")
end
end

View File

@@ -0,0 +1,340 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Diemaco C8A1"
SWEP.AbbrevName = "C8A1"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "4Assault Rifle"
SWEP.Description = "A close cousin to the classic American rifle with a slower but more controllable rate of fire."
SWEP.Description_Quote = "Green and very, very mean."
SWEP.Trivia_Caliber = "5.56x45mm"
SWEP.Trivia_Manufacturer = "Colt Canada"
SWEP.Trivia_Year = "1994"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_m4.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_m4.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 14,
Damage_Min = 8,
Range_Min = 600,
Range_Max = 2000,
RPM = 650,
RecoilSpreadPenalty = 0.002,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 9,
Damage_Min = 5,
Range_Min = 600,
Range_Max = 2800,
RPM = 700,
RecoilSpreadPenalty = 0.0017,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilMaximum = 25,
RecoilPerShot = 2,
RecoilDissipationRate = 20
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.AssaultRifle
// "ballistics"
SWEP.Damage_Max = 22
SWEP.Damage_Min = 15
SWEP.Range_Min = 1200
SWEP.Range_Max = 2800
SWEP.Penetration = 7 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.7
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 25000
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 700
SWEP.Spread = 0.003
SWEP.RecoilSpreadPenalty = 0.0017
SWEP.HipFireSpreadPenalty = 0.04
SWEP.PeekPenaltyFraction = 0.2
SWEP.ShootTimeMult = 0.5
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 10
SWEP.RecoilResetTime = 0
SWEP.RecoilDissipationRate = 35
SWEP.RecoilFirstShotMult = 1
SWEP.RecoilVisualKick = 0.75
SWEP.RecoilKick = 3
SWEP.RecoilStability = 0.25
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.925
SWEP.ShootingSpeedMult = 0.8
SWEP.SightedSpeedMult = 0.65
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.36
SWEP.SprintToFireTime = 0.38
SWEP.Sway = 1.25
SWEP.ScopedSway = 0.15
SWEP.FreeAimMaxAngle = 4.5
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -6)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0.18, 0.9, 0)
SWEP.SightPos = Vector(-4.15, -7.5, -4.3)
SWEP.CorrectivePos = Vector(-0.05, 0, 0.05)
SWEP.CorrectiveAng = Angle(0.03, 0.45, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint/magazines/m4.mdl"
SWEP.DropMagazineImpact = "metal"
SWEP.ReloadUpInTime = 1.3
SWEP.DropMagazineTime = 0.4
// sounds
local path = "TacRP/weapons/m4/m4_"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 120
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["fire_iron"] = "dryfire",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -1, -0.1),
vm_ang = Angle(0, 0.4, 0),
t = 0.25,
tmax = 0.25,
}
// attachments
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
},
["sights"] = {
BGs_VM = {
{2, 1}
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb_nookp7", "optic_medium", "optic_sniper"},
InstalledElements = {"sights"},
Bone = "ValveBiped.m4_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
VMScale = 1,
Pos_VM = Vector(-5.5, -0.05, 6),
Pos_WM = Vector(0.75, 5, 1.15),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90 + 3.5, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.m4_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
Pos_VM = Vector(-3.95, 0, 23),
Pos_WM = Vector(1.4, 21, -0.5),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -90 + 3.5, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.m4_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
Pos_VM = Vector(-3.9, -1.2, 13.5),
Pos_WM = Vector(2, 13, -0.5),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(-90, -90 + 3.5, 0),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock2", "acc_sling", "acc_duffle", "perk_extendedmag"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("TacInt_m4.Remove_Clip", path .. "remove_clip.wav")
addsound("TacInt_m4.Insert_Clip", path .. "insert_clip.wav")
addsound("TacInt_m4.Insert_Clip-mid", path .. "insert_clip-mid.wav")
addsound("TacInt_m4.bolt_action", path .. "bolt_action.wav")
addsound("TacInt_m4.bolt_slap", path .. "bolt_slap.wav")
addsound("TacInt_m4.throw_catch", path .. "throw_catch.wav")

View File

@@ -0,0 +1,147 @@
SWEP.Base = "tacrp_base_knife"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Нож"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "9Special"
SWEP.SubCatType = "8Bladed Melee"
SWEP.Description = "Military standard-issue knife that can be mounted on a weapon as a bayonet. Nothing stopping you from using it like a normal knife, however."
SWEP.Credits = "Assets: BrainBread 2"
SWEP.ViewModel = "models/weapons/tacint_melee/v_bayonet.mdl"
SWEP.WorldModel = "models/weapons/tacint_melee/w_bayonet.mdl"
SWEP.Slot = 0
SWEP.MeleeDamage = 35
SWEP.MeleeAttackTime = 0.4
SWEP.MeleeAttackMissTime = 0.5
SWEP.MeleeDamageType = DMG_SLASH
SWEP.MeleeThrowForce = 1200
SWEP.MeleePerkStr = 0.45
SWEP.MeleePerkAgi = 0.5
SWEP.MeleePerkInt = 0.55
// hold types
SWEP.HoldType = "knife"
SWEP.HoldTypeSprint = "knife"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_PISTOL
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_PISTOL
SWEP.GestureBash = ACT_HL2MP_GESTURE_RANGE_ATTACK_KNIFE
SWEP.GestureBash2 = ACT_HL2MP_GESTURE_RANGE_ATTACK_MELEE
SWEP.MidAirSpreadPenalty = 0
SWEP.PassiveAng = Angle(-2.5, 0, 0)
SWEP.PassivePos = Vector(1, 0, -5)
SWEP.SprintAng = Angle(0, 0, 0)
SWEP.SprintPos = Vector(2, 0, -5)
SWEP.CustomizeAng = Angle(0, 25, 0)
SWEP.CustomizePos = Vector(2, 0, -12)
SWEP.SprintMidPoint = {
Pos = Vector(2, 0, -5),
Ang = Angle(0, 0, 0)
}
SWEP.HolsterVisible = false
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_GEAR
SWEP.HolsterPos = Vector(2, 0, 0)
SWEP.HolsterAng = Angle(-90, -90, 15)
// sounds
local path = "tacrp/weapons/knife/"
SWEP.AnimationTranslationTable = {
["deploy"] = "deploy",
["melee"] = {"slash_left1", "slash_left2", "slash_right1", "slash_right2"},
["melee2"] = {"slash_forward1", "slash_forward2"},
["meleethrow"] = {"knifethrow"},
}
SWEP.Sound_MeleeHit = {
path .. "/scrape_metal-1.wav",
path .. "/scrape_metal-2.wav",
path .. "/scrape_metal-3.wav",
}
SWEP.Sound_MeleeHitBody = {
path .. "/flesh_hit-1.wav",
path .. "/flesh_hit-2.wav",
path .. "/flesh_hit-3.wav",
path .. "/flesh_hit-4.wav",
path .. "/flesh_hit-5.wav",
}
SWEP.Sound_MeleeSwing = {
path .. "swing-1.wav",
path .. "swing-2.wav",
path .. "swing-3.wav",
path .. "swing-4.wav",
path .. "swing-5.wav",
path .. "swing-6.wav",
}
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Technique",
Category = "melee_tech",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[2] = {
PrintName = "Special",
Category = "melee_spec",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
}
SWEP.FreeAim = false
SWEP.DrawCrosshair = true
SWEP.DrawCrosshairInSprint = true
SWEP.CrosshairStatic = true
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_knife2.deploy", "tacrp/magtap.ogg")
function SWEP:PrimaryAttack()
local stop = self:RunHook("Hook_PreShoot")
if stop then return end
self:Melee()
return
end
function SWEP:ThinkSprint()
end
function SWEP:ThinkSights()
end
SWEP.AutoSpawnable = false

View File

@@ -0,0 +1,310 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
DEFINE_BASECLASS( "tacrp_base" )
// names and stuff
SWEP.PrintName = "Аптечка первой помощи"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.NoAimAssist = true
SWEP.SubCatTier = "9Special"
SWEP.SubCatType = "9Equipment"
SWEP.Description = "Compact pack of medical supplies for treating wounds."
SWEP.Description_Quote = "\"Keep still, let me patch you up.\"" -- Left 4 Dead 1/2
SWEP.Credits = "Model/Texture: Left 4 Dead 2\nAnimation: Arqu"
SWEP.ViewModel = "models/weapons/tacint/v_medkit.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_medkit.mdl"
SWEP.NoRanger = true
SWEP.NoStatBox = true
SWEP.HUDAmmoMeter = true
SWEP.Slot = 4
SWEP.NPCUsable = false
SWEP.FreeAim = false
// misc. shooting
SWEP.CanBlindFire = false
SWEP.Ammo = ""
SWEP.ClipSize = 30
// handling
SWEP.NoBuffer = true
SWEP.Firemode = 0
SWEP.MoveSpeedMult = 1
SWEP.MeleeSpeedMultTime = 2 // seconds to apply slow down for
SWEP.SprintToFireTime = 0.25
SWEP.MidAirSpreadPenalty = 0
SWEP.MoveSpreadPenalty = 0
SWEP.HipFireSpreadPenalty = 0
SWEP.Scope = false
SWEP.NoSecondaryMelee = true
// hold types
SWEP.HoldType = "slam"
SWEP.HoldTypeSprint = "normal"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_PISTOL
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_PISTOL
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(-2, 0, -3)
SWEP.SprintAng = Angle(0, 0, 0)
SWEP.SprintPos = Vector(2, 0, -4)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_GEAR
SWEP.HolsterPos = Vector(-3, -5, 0)
SWEP.HolsterAng = Angle(-90, -90, 15)
SWEP.SprintMidPoint = {
Pos = Vector(0.25, 2, 1),
Ang = Angle(0, -5, 10)
}
// sounds
SWEP.AnimationTranslationTable = {
["deploy"] = "draw",
["melee"] = {"melee1", "melee2"},
}
SWEP.NoHolsterAnimation = true
SWEP.HolsterTimeMult = 0.75
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Perk",
Category = {"perk_melee", "perk_throw", "perk_passive"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
}
}
function SWEP:Hook_GetHintCapabilities(tbl)
if TacRP.ConVars["medkit_heal_others"]:GetInt() > 0 then
tbl["+attack"] = {so = 0, str = "hint.medkit.others"}
end
if TacRP.ConVars["medkit_heal_self"]:GetInt() > 0 then
tbl["+attack2"] = {so = 0.1, str = "hint.medkit.self"}
end
end
SWEP.HealTarget = nil
SWEP.LoopSound = nil
function SWEP:PrimaryAttack()
if self:GetValue("Melee") and self:GetOwner():KeyDown(IN_USE) then
self.Primary.Automatic = true
self:Melee()
return
end
if self:StillWaiting() then return end
if self:GetCharge() then return end
if TacRP.ConVars["medkit_heal_others"]:GetInt() <= 0 then return end
local tr = util.TraceLine({
start = self:GetOwner():EyePos(),
endpos = self:GetOwner():EyePos() + (self:GetOwner():EyeAngles():Forward() * 32),
filter = self:GetOwner()
})
if !tr.Hit then return end
if !tr.Entity then return end
if !(tr.Entity:IsPlayer() or tr.Entity:IsNPC()) then return end
if tr.Entity:Health() >= tr.Entity:GetMaxHealth() then return end
self.HealTarget = tr.Entity
self.Primary.Automatic = false
self:PlayAnimation("unzip", 1, true)
self:SetCharge(true)
if self.LoopSound then
self.LoopSound:Stop()
self.LoopSound = nil
end
self.LoopSound = CreateSound(self, "tacrp/weapons/bandaging_1.wav")
self.LoopSound:Play()
end
function SWEP:OnRemove()
if self.LoopSound then
self.LoopSound:Stop()
self.LoopSound = nil
end
return BaseClass.OnRemove(self)
end
function SWEP:SecondaryAttack()
if self:StillWaiting() or !IsFirstTimePredicted() or self:GetCharge() then return end
if self:GetOwner():Health() >= self:GetOwner():GetMaxHealth() then return end
if TacRP.ConVars["medkit_heal_self"]:GetInt() <= 0 then return end
self.HealTarget = self:GetOwner()
self.Primary.Automatic = false
self.Secondary.Automatic = false
self:PlayAnimation("unzip", 1, true)
self:SetCharge(true)
if self.LoopSound then
self.LoopSound:Stop()
self.LoopSound = nil
end
self.LoopSound = CreateSound(self:GetOwner(), "tacrp/weapons/bandaging_1.wav")
self.LoopSound:Play()
end
function SWEP:Think()
if IsFirstTimePredicted() and self:GetCharge() and self:GetNextPrimaryFire() < CurTime() then
if !IsValid(self.HealTarget) or
self:Clip1() <= 0 or
(self.HealTarget:GetPos() - self:GetOwner():GetPos()):Length() > 64
or
(self.HealTarget:Health() >= self.HealTarget:GetMaxHealth()) or
!(self:GetOwner():KeyDown(IN_ATTACK) or self:GetOwner():KeyDown(IN_ATTACK2)) then
self.HealTarget = nil
self:SetCharge(false)
self:PlayAnimation("draw", 1, true)
if self.LoopSound then
self.LoopSound:Stop()
self.LoopSound = nil
end
else
if SERVER then
local selfheal = self.HealTarget == self:GetOwner()
local amt = TacRP.ConVars[selfheal and "medkit_heal_self" or "medkit_heal_others"]:GetInt()
local ret = {amt}
hook.Run("TacRP_MedkitHeal", self, self:GetOwner(), self.HealTarget, ret)
amt = ret and ret[1] or amt
self:SetClip1(self:Clip1() - 1)
self.HealTarget:SetHealth(math.min(self.HealTarget:Health() + amt, self.HealTarget:GetMaxHealth()))
end
self:SetNextPrimaryFire(CurTime() + TacRP.ConVars["medkit_interval"]:GetFloat())
end
end
return BaseClass.Think(self)
end
function SWEP:Regenerate()
if CLIENT then return end
if self:GetNextPrimaryFire() + 0.1 > CurTime() then return end
local amt = TacRP.ConVars["medkit_regen_amount"]:GetInt()
if amt == 0 then
if self:Clip1() == 0 then
self:Remove()
end
return
end
if TacRP.ConVars["medkit_regen_activeonly"]:GetBool()
and (!IsValid(self:GetOwner()) or self:GetOwner():GetActiveWeapon() != self) then return end
self:SetClip1(math.min(self:Clip1() + amt, self:GetValue("ClipSize")))
end
function SWEP:Holster(wep)
if self.LoopSound then
self.LoopSound:Stop()
self.LoopSound = nil
end
self:SetCharge(false)
self.HealTarget = nil
return BaseClass.Holster(self, wep)
end
function SWEP:OnRemove()
if game.SinglePlayer() then
self:CallOnClient("OnRemove")
end
if self.LoopSound then
self.LoopSound:Stop()
self.LoopSound = nil
end
return BaseClass.OnRemove(self)
end
function SWEP:Initialize()
self.ClipSize = TacRP.ConVars["medkit_clipsize"]:GetInt()
self:SetClip1(self:GetValue("ClipSize"))
self:SetCharge(false)
timer.Create("medkit_ammo" .. self:EntIndex(), TacRP.ConVars["medkit_regen_delay"]:GetFloat(), 0, function()
if !IsValid(self) then
if self.LoopSound then
self.LoopSound:Stop()
self.LoopSound = nil
end
timer.Stop("medkit_ammo" .. self:EntIndex())
return
end
if IsValid(self:GetOwner()) and self != self:GetOwner():GetActiveWeapon() then
if self.LoopSound then
self.LoopSound:Stop()
self.LoopSound = nil
end
end
self:Regenerate()
end)
return BaseClass.Initialize(self)
end
if engine.ActiveGamemode() == "terrortown" then
SWEP.HolsterVisible = false
SWEP.AutoSpawnable = false
SWEP.Kind = WEAPON_EQUIP2
SWEP.Slot = 6
SWEP.CanBuy = { ROLE_DETECTIVE, ROLE_TRAITOR }
SWEP.LimitedStock = true
SWEP.EquipMenuData = {
type = "Weapon",
desc = "Medical supplies for treating wounds.\nCharge regenrates over time.",
}
function SWEP:TTTBought(buyer)
end
end
function SWEP:Reload()
end // do nothing

View File

@@ -0,0 +1,360 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "HK MG4"
SWEP.AbbrevName = "MG4"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "1Elite"
SWEP.SubCatType = "5Machine Gun"
SWEP.Description = "Machine gun with huge volume of fire."
SWEP.Description_Quote = "The buzzsaw's great grandson."
SWEP.Trivia_Caliber = "5.56x45mm"
SWEP.Trivia_Manufacturer = "Heckler & Koch"
SWEP.Trivia_Year = "2005"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_mg4.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_mg4.mdl"
SWEP.Slot = 2
SWEP.SlotAlt = 3
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 26,
Damage_Min = 18,
ClipSize = 75,
},
[TacRP.BALANCE_TTT] = {
Description = "Machine gun with high damage but very low mobility.",
Damage_Max = 20,
Damage_Min = 12,
Range_Min = 750,
Range_Max = 3000,
ClipSize = 75,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 19,
Damage_Min = 14,
ClipSize = 100,
},
[TacRP.BALANCE_OLDSCHOOL] = {
Description = "Balanced light machine gun that can put down some serious firepower.",
ClipSize = 75,
RecoilSpreadPenalty = 0.0013,
ReloadTimeMult = 1.1
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.MachineGun
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.75
}
// "ballistics"
SWEP.Damage_Max = 28
SWEP.Damage_Min = 20
SWEP.Range_Min = 800
SWEP.Range_Max = 4000
SWEP.Penetration = 10
SWEP.ArmorPenetration = 0.8
SWEP.MuzzleVelocity = 17500
// misc. shooting
SWEP.Firemode = 2
SWEP.RPM = 750
SWEP.Spread = 0.005
SWEP.ShootTimeMult = 0.5
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 25
SWEP.RecoilResetTime = 0.15
SWEP.RecoilDissipationRate = 40
SWEP.RecoilFirstShotMult = 2
SWEP.RecoilVisualKick = 1
SWEP.RecoilKick = 5
SWEP.RecoilStability = 0.1
SWEP.HipFireSpreadPenalty = 0.025
SWEP.RecoilSpreadPenalty = 0.0009
SWEP.PeekPenaltyFraction = 0.125
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.85
SWEP.ShootingSpeedMult = 0.4
SWEP.SightedSpeedMult = 0.5
SWEP.ReloadSpeedMult = 0.1
SWEP.ReloadSpeedMultTime = 1
SWEP.AimDownSightsTime = 0.44
SWEP.SprintToFireTime = 0.48
SWEP.Sway = 2
SWEP.ScopedSway = 0.75
SWEP.FreeAimMaxAngle = 7
SWEP.Bipod = true
SWEP.BipodRecoil = 0.35
SWEP.BipodKick = 0.25
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -4, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(0, -4, -3)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(-0.11, -0.6, 0)
SWEP.SightPos = Vector(-4.55, -7.5, -3.7)
SWEP.CorrectivePos = Vector(0.025, 0, 0.125)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK2
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 100
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint/magazines/mg4.mdl"
SWEP.DropMagazineImpact = "metal"
SWEP.ReloadUpInTime = 3.5
SWEP.DropMagazineTime = 0.7
SWEP.BulletBodygroups = {
[1] = {5, 0},
[2] = {5, 1},
[3] = {5, 2},
[4] = {5, 3},
[5] = {5, 4},
[6] = {5, 5},
[7] = {5, 6},
}
SWEP.DefaultBodygroups = "000007"
// sounds
local path = "TacRP/weapons/mg4/"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Sound_Shoot_Silenced = "TacRP/weapons/g36k/g36k_fire_silenced-1.wav"
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_minimi"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["fire_iron"] = {"fire4_M", "fire3_M", "fire2_M", "fire1_M"},
["fire1"] = "fire1_L",
["fire2"] = "fire2_L",
["fire3"] = "fire3_L",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
// attachments
SWEP.AttachmentElements = {
["sights"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
},
},
["extendedbelt"] = {
BGs_VM = {
{2, 1}
},
},
["bipod"] = {
BGs_VM = {
{3, 1}
},
BGs_WM = {
{3, 1}
},
},
}
//ValveBiped.MG4_root
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium"},
Bone = "ValveBiped.feed_cover",
InstalledElements = {"sights"},
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
VMScale = 1.1,
Pos_VM = Vector(-0.75, 0, -3),
Pos_WM = Vector(8, 1.15, -7),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, 0, 180),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.MG4_root",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
Pos_VM = Vector(-5.5, 0, 32),
Pos_WM = Vector(33, 1.15, -5.75),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, 0, 180),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.MG4_root",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
Pos_VM = Vector(-5.225, -0.9, 19),
Pos_WM = Vector(21.5, 2, -5.25),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, 0, 90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "extendedbelt", "acc_duffle", "acc_bipod", "acc_sling"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
}
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("TacInt_mg4.Clip_Out", path .. "clip_out-1.wav")
addsound("TacInt_mg4.Clip_In", path .. "clip_in-1.wav")
addsound("TacInt_mg4.bolt_release", path .. "bolt_release-1.wav")
addsound("TacInt_mg4.bolt_back", path .. "bolt_back-1.wav")
addsound("TacInt_mg4.bolt_forward", path .. "bolt_forward-1.wav")
addsound("TacInt_mg4.feedcover_close", path .. "feed_cover_close-1.wav")
addsound("TacInt_mg4.feedcover_open", path .. "feed_cover_open-1.wav")
addsound("TacInt_mg4.insertbullets", path .. "insert_bullets-1.wav")
addsound("TacInt_mg4.deploy", path .. "deploy-1.wav")

View File

@@ -0,0 +1,355 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "HK MP5A3"
SWEP.AbbrevName = "MP5A3"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "3Security"
SWEP.SubCatType = "3Submachine Gun"
SWEP.Description = "Well-balanced submachine gun known for its precision."
SWEP.Description_Quote = "\"Now I have a machine gun. Ho, ho, ho.\""
SWEP.Trivia_Caliber = "9x19mm"
SWEP.Trivia_Manufacturer = "Heckler & Koch"
SWEP.Trivia_Year = "1966"
SWEP.Faction = TacRP.FACTION_NEUTRAL
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_mp5.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_mp5.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 20,
Damage_Min = 14,
Range_Min = 1500,
Range_Max = 4000,
HipFireSpreadPenalty = 0.025,
RecoilKick = 3.5,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 14,
Damage_Min = 9,
RecoilSpreadPenalty = 0.0015,
HipFireSpreadPenalty = 0.03,
RecoilMaximum = 12,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 8,
Damage_Min = 4,
Range_Min = 1500,
Range_Max = 4000,
HipFireSpreadPenalty = 0.02,
RecoilKick = 2,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilMaximum = 20,
RecoilDissipationRate = 25
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.SMG
// "ballistics"
SWEP.Damage_Max = 27
SWEP.Damage_Min = 17
SWEP.Range_Min = 800 // distance for which to maintain maximum damage
SWEP.Range_Max = 2500 // distance at which we drop to minimum damage
SWEP.Penetration = 6 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.7
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 13500
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 750
SWEP.Spread = 0.0038
SWEP.ShootTimeMult = 0.5
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 12
SWEP.RecoilResetTime = 0
SWEP.RecoilDissipationRate = 40
SWEP.RecoilFirstShotMult = 0.9
SWEP.RecoilVisualKick = 0.5
SWEP.RecoilKick = 3
SWEP.RecoilStability = 0.4
SWEP.RecoilSpreadPenalty = 0.002
SWEP.HipFireSpreadPenalty = 0.025
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.95
SWEP.ShootingSpeedMult = 0.85
SWEP.SightedSpeedMult = 0.7
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.33
SWEP.SprintToFireTime = 0.33
SWEP.Sway = 0.75
SWEP.ScopedSway = 0.25
SWEP.FreeAimMaxAngle = 3.5
// hold types
SWEP.HoldType = "ar2"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -4, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(0, -4, -3)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(8, -1, -2)
SWEP.SightAng = Angle(-0.02, 0.75, 0)
SWEP.SightPos = Vector(-4.555, -7.5, -3.6)
SWEP.CorrectivePos = Vector(0.025, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 0, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 30
SWEP.DefaultAmmo = 0
SWEP.Ammo = "pistol"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint/magazines/mp5.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.55
SWEP.DropMagazineTime = 1
// sounds
local path = "TacRP/weapons/mp5/mp5_"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 110
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 1
// anims
SWEP.AnimationTranslationTable = {
["fire_iron"] = {"fire1_L", "fire1_M"},
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -1, -0.1),
vm_ang = Angle(0, 0.4, 0),
t = 0.25,
tmax = 0.25,
}
// attachments
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
BGs_WM = {
{1, 1}
}
},
["optic"] = {
BGs_VM = {
{2, 1}
},
},
["tactical"] = {
BGs_VM = {
{3, 1}
},
},
}
SWEP.NoRMR = true
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium"},
Bone = "ValveBiped.mp5_rootbone",
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
InstalledElements = {"optic"},
Pos_VM = Vector(-6.25, -0.3, 6.5),
Pos_WM = Vector(7, 1.5, -6.5),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -3.5, 180),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.mp5_rootbone",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
Pos_VM = Vector(-4.32, -0.3, 20.5),
Pos_WM = Vector(24, 2.5, -5.25),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -3.5, 180),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.mp5_rootbone",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
InstalledElements = {"tactical"},
Pos_VM = Vector(-4, 0.5, 11),
Pos_WM = Vector(14, 1.3, -5),
Ang_VM = Angle(90, 0, 90),
Ang_WM = Angle(0, -3.5, -90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock2", "acc_sling", "acc_duffle", "acc_extmag_smg"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_pistol"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
}
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("TacInt_mp5.remove_clip", path .. "remove_clip.wav")
addsound("TacInt_mp5.insert_clip", path .. "insert_clip.wav")
addsound("TacInt_mp5.insert_clip-mid", path .. "insert_clip-mid.wav")
addsound("TacInt_mp5.HK_Slap", path .. "hk_slap.wav")
addsound("TacInt_mp5.bolt_back", path .. "bolt_back.wav")
addsound("TacInt_mp5.fire_select", {
path .. "fire_select-1.wav",
path .. "fire_select-2.wav",
path .. "fire_select-3.wav",
})

View File

@@ -0,0 +1,340 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "HK MP7"
SWEP.AbbrevName = "MP7"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "3Submachine Gun"
SWEP.Description = "PDW with superb handling and close range effectiveness. High velocity rounds retain effectiveness at range and pierces armor easily."
SWEP.Description_Quote = "\"You've got to cock it motherfucker.\"" -- Big Game (2014)
SWEP.Trivia_Caliber = "4.6x30mm"
SWEP.Trivia_Manufacturer = "Heckler & Koch"
SWEP.Trivia_Year = "2001"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_mp7.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_mp7.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 12,
Damage_Min = 7,
Range_Min = 1000,
Range_Max = 2000,
RPM = 750,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 10,
Damage_Min = 5,
RPM = 800,
RecoilSpreadPenalty = 0.003,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilMaximum = 20,
RecoilSpreadPenalty = 0.0035
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.SMG
// "ballistics"
SWEP.Damage_Max = 16
SWEP.Damage_Min = 14
SWEP.Range_Min = 800 // distance for which to maintain maximum damage
SWEP.Range_Max = 3500 // distance at which we drop to minimum damage
SWEP.Penetration = 10 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.85
SWEP.ArmorBonus = 2
SWEP.MuzzleVelocity = 23500
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 850
SWEP.Spread = 0.008
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 11
SWEP.RecoilResetTime = 0
SWEP.RecoilDissipationRate = 33
SWEP.RecoilFirstShotMult = 1.5
SWEP.RecoilVisualKick = 1
SWEP.RecoilKick = 3
SWEP.RecoilStability = 0.5
SWEP.RecoilSpreadPenalty = 0.0018
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.975
SWEP.ShootingSpeedMult = 0.8
SWEP.SightedSpeedMult = 0.75
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.3
SWEP.SprintToFireTime = 0.28
SWEP.Sway = 0.75
SWEP.ScopedSway = 0.25
SWEP.FreeAimMaxAngle = 4
// hold types
SWEP.HoldType = "smg"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -4, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(0, -4, -3)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0.1, 1, 0)
SWEP.SightPos = Vector(-3.22, -2, -4.2)
SWEP.CorrectivePos = Vector(0.04, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 6, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 40
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.Ammo_Expanded = "ti_pdw"
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint/magazines/mp7.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.2
SWEP.DropMagazineTime = 0.4
// sounds
local path = "tacrp/weapons/mp7/mp7_"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 115
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_ak47"
SWEP.EjectEffect = 1
// anims
SWEP.AnimationTranslationTable = {
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -1, -0.1),
vm_ang = Angle(0, 0.4, 0),
t = 0.25,
tmax = 0.25,
}
// attachments
SWEP.AttachmentElements = {
["foldstock"] = {
BGs_VM = {
{1, 1}
},
},
["optic"] = {
BGs_VM = {
{2, 1}
},
},
["rail"] = {
BGs_VM = {
{3, 1}
},
},
}
SWEP.NoRMR = true
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium"},
Bone = "ValveBiped.mp7_rootbone",
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
InstalledElements = {"optic"},
Pos_VM = Vector(-4.25, 0, 1.5),
Pos_WM = Vector(4, 1.5, -6),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -3.5, 180),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.mp7_rootbone",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
VMScale = 0.8,
Pos_VM = Vector(-2.25, 0.1, 11.75),
Pos_WM = Vector(18, 2.25, -4.25),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -3.5, 180),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.mp7_rootbone",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
InstalledElements = {"rail"},
Pos_VM = Vector(-2.2, -0.5, 5),
Pos_WM = Vector(10, 1.3, -4),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, -3.5, -90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_foldstock2", "acc_sling", "acc_duffle", "acc_extmag_smg"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
}
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
local path_mp5 = "tacrp/weapons/mp5/mp5_"
addsound("tacint_mp7.remove_clip", path .. "remove_clip.wav")
addsound("tacint_mp7.insert_clip", path .. "insert_clip.wav")
addsound("tacint_mp7.bolt_action", path .. "bolt_action.wav")
addsound("tacint_mp7.forearm_deploy", path .. "forearm_deploy.wav")
addsound("tacint_mp5.fire_select", {
path_mp5 .. "fire_select-1.wav",
path_mp5 .. "fire_select-2.wav",
path_mp5 .. "fire_select-3.wav",
})

View File

@@ -0,0 +1,331 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "Manurhin MR96"
SWEP.AbbrevName = "MR96"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "2Magnum Pistol"
SWEP.Description = "Magnum revolver with good handling and stopping power. Accurate, but hard to fire rapidly."
SWEP.Description_Quote = "Legend has it a stainless steel version exists..." -- One of the thugs in Ghost in the Shell 2: Innocence (2004) uses a stainless steel MR96
SWEP.Trivia_Caliber = ".357 Magnum"
SWEP.Trivia_Manufacturer = "Chapuis Armes"
SWEP.Trivia_Year = "1996"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_mr96.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_mr96.mdl"
SWEP.Slot = 1
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 35,
Damage_Min = 20,
Range_Min = 600,
Range_Max = 1600,
RPM = 120,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4,
[HITGROUP_CHEST] = 1.25,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.75
},
RecoilMaximum = 2,
RecoilDissipationRate = 2.5,
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 55,
Damage_Min = 24,
RPM = 120,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilDissipationRate = 4
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.Magnum
// "ballistics"
SWEP.Damage_Max = 54 // damage at minimum range
SWEP.Damage_Min = 28 // damage at maximum range
SWEP.Range_Min = 300 // distance for which to maintain maximum damage
SWEP.Range_Max = 2500 // distance at which we drop to minimum damage
SWEP.Penetration = 6 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.9
SWEP.MuzzleVelocity = 12500
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.75
}
// misc. shooting
SWEP.Firemode = 1
SWEP.FiremodeName = "Double-Action" // only used externally for firemode name distinction
SWEP.RPM = 140
SWEP.Spread = 0.001
SWEP.ShootTimeMult = 1
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 2
SWEP.RecoilResetTime = 0
SWEP.RecoilDissipationRate = 9
SWEP.RecoilFirstShotMult = 0.9
SWEP.RecoilVisualKick = 5
SWEP.RecoilKick = 9
SWEP.RecoilStability = 0.5
SWEP.RecoilSpreadPenalty = 0.018
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.9
SWEP.ShootingSpeedMult = 0.75
SWEP.SightedSpeedMult = 0.8
SWEP.ReloadSpeedMult = 0.75
SWEP.AimDownSightsTime = 0.22
SWEP.SprintToFireTime = 0.3
SWEP.FreeAimMaxAngle = 4.5
// hold types
SWEP.HoldType = "revolver"
SWEP.HoldTypeSprint = "normal"
SWEP.HoldTypeBlindFire = "pistol"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_REVOLVER
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_REVOLVER
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -4)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(3, -2, -5)
SWEP.BlindFireSuicideAng = Angle(-125, 0, 45)
SWEP.BlindFireSuicidePos = Vector(25, 12, -6)
SWEP.SprintAng = Angle(0, 30, 0)
SWEP.SprintPos = Vector(2, 0, -12)
SWEP.SightAng = Angle(-0.15, 1, 0)
SWEP.SightPos = Vector(-3.5, 0, -3.7)
SWEP.CorrectivePos = Vector(0, 0, 0.1)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_PISTOL
SWEP.HolsterPos = Vector(0, 3, -4)
SWEP.HolsterAng = Angle(90, 0, 0)
SWEP.Sway = 1.5
SWEP.ScopedSway = 0.6
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 6
SWEP.DefaultAmmo = 0
SWEP.Ammo = "357"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.ReloadTimeMult = 1
SWEP.ReloadUpInTime = 1.35
SWEP.JamSkipFix = true
// sounds
local path = "TacRP/weapons/mr96/"
SWEP.Sound_Shoot = {
"^" .. path .. "mr96_fire-1.wav",
"^" .. path .. "mr96_fire-2.wav",
"^" .. path .. "mr96_fire-3.wav",
}
SWEP.Vol_Shoot = 130
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 2
SWEP.QCA_Eject = 0
SWEP.EjectEffect = 0
SWEP.MuzzleEffect = "muzzleflash_1"
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "draw",
["fire"] = {"shoot1", "shoot2", "shoot3"},
["fire_iron"] = "shoot1",
["blind_fire"] = {"blind_shoot1", "blind_shoot2"},
["melee"] = {"melee1", "melee2"},
["jam"] = "draw"
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -3, -4.5),
vm_ang = Angle(0, 15, 0),
t = 0.5,
tmax = 0.5,
bones = {
{
bone = "ValveBiped.cylinder",
ang = Angle(-60, 0, 0),
t0 = 0,
t1 = 0.25,
},
{
bone = "ValveBiped.hammer",
ang = Angle(35, 0, 0),
t0 = 0.05,
t1 = 0.15,
},
{
bone = "ValveBiped.Bip01_R_Finger1",
ang = Angle(0, -15, 0),
t0 = 0,
t1 = 0.2,
},
{
bone = "ValveBiped.Bip01_R_Finger11",
ang = Angle(-35, 0, 0),
t0 = 0,
t1 = 0.15,
},
},
}
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium"},
Bone = "ValveBiped.mr96_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
VMScale = 0.8,
WMScale = 1,
Pos_VM = Vector(-3.9, -0.125, 6.5),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 1.5, -0.8),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.mr96_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
VMScale = 1,
WMScale = 1,
Pos_VM = Vector(-2.25, -0.125, 9),
Ang_VM = Angle(90, 0, 180),
Pos_WM = Vector(0, 8, -2.25),
Ang_WM = Angle(0, -90, 180),
},
[3] = {
PrintName = "Accessory",
Category = {"acc", "acc_holster", "acc_brace", "acc_bipod"}, // yes, MR96 with bipod is a real thing!
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[4] = {
PrintName = "Trigger",
Category = {"trigger_revolver"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Ammo",
Category = {"ammo_pistol", "ammo_roulette"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
}
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("TacInt_MR96.Release_Cylinder", path .. "mr96_release_cylinder.wav")
addsound("TacInt_MR96.Eject_Shells", path .. "mr96_eject_shells.wav")
addsound("TacInt_MR96.Insert_Bullets", path .. "mr96_insert_bullets.wav")
addsound("TacInt_MR96.Shut_Cylinder", path .. "mr96_shut_cylinder.wav")
addsound("TacInt_MR96.Insert_Bullets-Mid", path .. "mr96_insert_bullets-mid.wav")
addsound("TacInt_MR96.Cock_Hammer", path .. "mr96_cockhammer.wav")
addsound("TacInt_MR96.Deploy", path .. "mr96_deploy.wav")

View File

@@ -0,0 +1,35 @@
AddCSLuaFile()
SWEP.Base = "tacrp_base_nade"
SWEP.Spawnable = TacRP.AreTheGrenadeAnimsReadyYet
SWEP.IconOverride = "entities/tacrp_ammo_charge.png"
// names and stuff
SWEP.PrintName = "Взрывной заряд"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.ViewModel = "models/weapons/tacint/v_throwable_breach.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_frag.mdl"
SWEP.ViewModelFOV = 65
SWEP.Slot = 4
SWEP.PrimaryGrenade = "charge"
SWEP.FiremodeName = "Throw"
SWEP.AnimationTranslationTable = {
["prime_grenade"] = "pullpin",
["throw_grenade"] = "throw",
["throw_grenade_underhand"] = "throw",
}
SWEP.TTTReplace = {} // {["weapon_ttt_confgrenade"] = 0.5}
SWEP.Attachments = {}
SWEP.HoldType = "melee"
SWEP.HoldTypeSprint = "normal"
SWEP.HoldTypeBlindFire = false

View File

@@ -0,0 +1,35 @@
AddCSLuaFile()
SWEP.Base = "tacrp_base_nade"
SWEP.Spawnable = TacRP.AreTheGrenadeAnimsReadyYet
SWEP.IconOverride = "entities/tacrp_ammo_flashbang.png"
// names and stuff
SWEP.PrintName = "Светошумовая граната"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.ViewModel = "models/weapons/tacint/v_throwable_flashbang.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_flashbang.mdl"
SWEP.ViewModelFOV = 65
SWEP.Slot = 4
SWEP.PrimaryGrenade = "flashbang"
SWEP.FiremodeName = "Throw"
SWEP.AnimationTranslationTable = {
["prime_grenade"] = "pullpin",
["throw_grenade"] = "throw",
["throw_grenade_underhand"] = "throw",
}
SWEP.TTTReplace = {["weapon_ttt_confgrenade"] = 1}
SWEP.Attachments = {}
SWEP.HoldType = "melee"
SWEP.HoldTypeSprint = "normal"
SWEP.HoldTypeBlindFire = false

View File

@@ -0,0 +1,35 @@
AddCSLuaFile()
SWEP.Base = "tacrp_base_nade"
SWEP.Spawnable = TacRP.AreTheGrenadeAnimsReadyYet
SWEP.IconOverride = "entities/tacrp_ammo_frag.png"
// names and stuff
SWEP.PrintName = "Осколочная граната"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.ViewModel = "models/weapons/tacint/v_throwable_frag.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_frag.mdl"
SWEP.ViewModelFOV = 65
SWEP.Slot = 4
SWEP.PrimaryGrenade = "frag"
SWEP.FiremodeName = "Throw"
SWEP.AnimationTranslationTable = {
["prime_grenade"] = "pullpin",
["throw_grenade"] = "throw",
["throw_grenade_underhand"] = "throw",
}
SWEP.TTTReplace = {}
SWEP.AutoSpawnable = false
SWEP.Attachments = {}
SWEP.HoldType = "melee"
SWEP.HoldTypeSprint = "normal"
SWEP.HoldTypeBlindFire = false

View File

@@ -0,0 +1,34 @@
AddCSLuaFile()
SWEP.Base = "tacrp_base_nade"
SWEP.Spawnable = TacRP.AreTheGrenadeAnimsReadyYet
SWEP.IconOverride = "entities/tacrp_ammo_smoke.png"
// names and stuff
SWEP.PrintName = "Дымовая граната"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.ViewModel = "models/weapons/tacint/v_throwable_smoke.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_smoke.mdl"
SWEP.ViewModelFOV = 65
SWEP.Slot = 4
SWEP.PrimaryGrenade = "smoke"
SWEP.FiremodeName = "Throw"
SWEP.AnimationTranslationTable = {
["prime_grenade"] = "pullpin",
["throw_grenade"] = "throw",
["throw_grenade_underhand"] = "throw",
}
SWEP.TTTReplace = {["weapon_ttt_smokegrenade"] = 1}
SWEP.Attachments = {}
SWEP.HoldType = "melee"
SWEP.HoldTypeSprint = "normal"
SWEP.HoldTypeBlindFire = false

View File

@@ -0,0 +1,34 @@
AddCSLuaFile()
SWEP.Base = "tacrp_base_nade"
SWEP.Spawnable = TacRP.AreTheGrenadeAnimsReadyYet
SWEP.IconOverride = "entities/tacrp_ammo_fire.png"
// names and stuff
SWEP.PrintName = "Термитная граната"
SWEP.Category = "[FT] Специальное Оружие"
SWEP.ViewModel = "models/weapons/tacint/v_throwable_thermite.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_flashbang.mdl"
SWEP.ViewModelFOV = 65
SWEP.Slot = 4
SWEP.PrimaryGrenade = "thermite"
SWEP.FiremodeName = "Throw"
SWEP.AnimationTranslationTable = {
["prime_grenade"] = "pullpin",
["throw_grenade"] = "throw",
["throw_grenade_underhand"] = "throw",
}
SWEP.TTTReplace = {["weapon_zm_molotov"] = 1}
SWEP.Attachments = {}
SWEP.HoldType = "melee"
SWEP.HoldTypeSprint = "normal"
SWEP.HoldTypeBlindFire = false

View File

@@ -0,0 +1,367 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "SIG P250"
SWEP.AbbrevName = "P250"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "1Pistol"
SWEP.Description = "Powerful handgun that exchanges capacity for damage and precision."
SWEP.Description_Quote = "\"You wait until they get close and aim for the face. You understand?\"" -- Watch_Dogs (2014)
SWEP.Trivia_Caliber = ".357 SIG"
SWEP.Trivia_Manufacturer = "SIG Sauer, Inc."
SWEP.Trivia_Year = "2007"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_p250.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_p250.mdl"
SWEP.Slot = 1
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 32,
Damage_Min = 20,
Range_Min = 900,
Range_Max = 2800,
ArmorPenetration = 0.65,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3.25,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_TTT] = {
Description = "Powerful handgun that exchanges fire rate for damage and precision.",
Damage_Max = 22,
Damage_Min = 12,
Range_Min = 800,
Range_Max = 2000,
RPM = 200,
RPMMultSemi = 1,
RecoilResetInstant = true,
RecoilMaximum = 5,
RecoilResetTime = 0.2,
RecoilDissipationRate = 5.5,
RecoilFirstShotMult = 0.8,
RecoilSpreadPenalty = 0.012,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 0.9,
[HITGROUP_RIGHTARM] = 0.9,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 18,
Damage_Min = 12,
Range_Min = 900,
Range_Max = 2800,
RPM = 450,
},
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.Pistol
// "ballistics"
SWEP.Damage_Max = 28
SWEP.Damage_Min = 15
SWEP.Range_Min = 800 // distance for which to maintain maximum damage
SWEP.Range_Max = 2500 // distance at which we drop to minimum damage
SWEP.Penetration = 7 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.775
SWEP.ArmorBonus = 1
SWEP.MuzzleVelocity = 11000
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 4.5,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
}
// misc. shooting
SWEP.Firemode = 1
SWEP.RPM = 500
SWEP.RPMMultSemi = 0.7
SWEP.Spread = 0.004
SWEP.ShootTimeMult = 0.5
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 3
SWEP.RecoilResetTime = 0.02
SWEP.RecoilDissipationRate = 12
SWEP.RecoilFirstShotMult = 1
SWEP.RecoilVisualKick = 1.5
SWEP.RecoilKick = 5
SWEP.RecoilStability = 0.6
SWEP.RecoilSpreadPenalty = 0.0065
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.975
SWEP.ShootingSpeedMult = 0.9
SWEP.SightedSpeedMult = 0.8
SWEP.ReloadSpeedMult = 0.75
SWEP.AimDownSightsTime = 0.25
SWEP.SprintToFireTime = 0.25
SWEP.Sway = 1
SWEP.ScopedSway = 0.5
SWEP.FreeAimMaxAngle = 3
// hold types
SWEP.HoldType = "revolver"
SWEP.HoldTypeSprint = "normal"
SWEP.HoldTypeBlindFire = "pistol"
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_PISTOL
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_PISTOL
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -2, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(0, -2, -5)
SWEP.BlindFireSuicideAng = Angle(-130, 0, 45)
SWEP.BlindFireSuicidePos = Vector(25, 15, -6)
SWEP.SprintAng = Angle(0, 30, 0)
SWEP.SprintPos = Vector(2, 0, -12)
SWEP.SightAng = Angle(0.02, 0.15, 0)
SWEP.SightPos = Vector(-3.45, 0, -3.35)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_PISTOL
SWEP.HolsterPos = Vector(0, 3, -4)
SWEP.HolsterAng = Angle(90, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 12
SWEP.DefaultAmmo = 0
SWEP.Ammo = "pistol"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.Ammo_Expanded = "ti_pistol_heavy"
SWEP.ReloadTimeMult = 1.1
SWEP.DropMagazineModel = "models/weapons/tacint/magazines/p250.mdl"
SWEP.DropMagazineImpact = "pistol"
SWEP.ReloadUpInTime = 0.9
SWEP.DropMagazineTime = 0.2
// sounds
local path = "TacRP/weapons/p250/p250_"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 110
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 4
SWEP.MuzzleEffect = "muzzleflash_pistol"
SWEP.EjectEffect = 1
// anims
SWEP.AnimationTranslationTable = {
["deploy"] = "draw",
["fire"] = {"shoot1", "shoot2", "shoot3"},
["blind_fire"] = {"blind_shoot1", "blind_shoot2", "blind_shoot3"},
["melee"] = {"melee1", "melee2"}
}
SWEP.ProceduralIronFire = {
vm_pos = Vector(0, -0.5, -0.6),
vm_ang = Angle(0, 2, 0),
t = 0.2,
tmax = 0.2,
bones = {
{
bone = "ValveBiped.slide",
pos = Vector(0, 0, -3),
t0 = 0,
t1 = 0.1,
},
{
bone = "ValveBiped.hammer",
ang = Angle(-15, 0, 0),
t0 = 0,
t1 = 0.15,
},
{
bone = "ValveBiped.Bip01_R_Finger1",
ang = Angle(0, -15, 0),
t0 = 0,
t1 = 0.2,
},
{
bone = "ValveBiped.Bip01_R_Finger11",
ang = Angle(-35, 0, 0),
t0 = 0,
t1 = 0.15,
},
},
}
SWEP.LastShot = true
// attachments
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = "optic_pistol",
Bone = "ValveBiped.slide",
WMBone = "Box01",
AttachSound = "TacRP/weapons/optic_on.wav",
DetachSound = "TacRP/weapons/optic_off.wav",
VMScale = 1,
WMScale = 1,
Pos_VM = Vector(0.01, 0, 0),
Ang_VM = Angle(0, 90, 180),
Pos_WM = Vector(0, -1, -1),
Ang_WM = Angle(0, -90, 0),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "ValveBiped.barrel_assembly",
WMBone = "Box01",
AttachSound = "TacRP/weapons/silencer_on.wav",
DetachSound = "TacRP/weapons/silencer_off.wav",
VMScale = 0.5,
WMScale = 0.5,
Pos_VM = Vector(-0.6, 0.45, 6),
Ang_VM = Angle(90, 0, 0),
Pos_WM = Vector(0, 8, -1.5),
Ang_WM = Angle(0, -90, 0),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "ValveBiped.p250_rootbone",
WMBone = "Box01",
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
VMScale = 1.1,
WMScale = 1.3,
Pos_VM = Vector(-2, 0, 5.25),
Ang_VM = Angle(90, 0, 180),
Pos_WM = Vector(0, 5, -2.75),
Ang_WM = Angle(0, -90, 180),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_extmag_pistol", "acc_holster", "acc_brace"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_semi"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_pistol"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("TacInt_p250.clip_in", path .. "clip_in.wav")
addsound("TacInt_p250.clip_in-mid", path .. "clip_in-mid.wav")
addsound("TacInt_p250.clip_out", path .. "clip_out.wav")
addsound("TacInt_p250.slide_action", path .. "slide_action.wav")
addsound("TacInt_p250.slide_shut", path .. "slide_shut.wav")
addsound("TacInt_p250.cock_hammer", path .. "cockhammer.wav")

View File

@@ -0,0 +1,319 @@
SWEP.Base = "tacrp_base"
SWEP.Spawnable = true
AddCSLuaFile()
// names and stuff
SWEP.PrintName = "FN P90"
SWEP.AbbrevName = "P90"
SWEP.Category = "[FT] Оружие"
SWEP.SubCatTier = "2Operator"
SWEP.SubCatType = "3Submachine Gun"
SWEP.Description = "Bullpup PDW with a generous top-loaded magazine and controllable spread. High velocity rounds retain effectiveness at range and pierces armor easily."
SWEP.Description_Quote = "\"This is a weapon of war, it's made to kill your enemy.\"" // SG-1 Stargate
SWEP.Trivia_Caliber = "5.7x28mm"
SWEP.Trivia_Manufacturer = "FN Herstal"
SWEP.Trivia_Year = "1990"
SWEP.Faction = TacRP.FACTION_COALITION
SWEP.Credits = "Assets: Tactical Intervention"
SWEP.ViewModel = "models/weapons/tacint/v_p90.mdl"
SWEP.WorldModel = "models/weapons/tacint/w_p90.mdl"
SWEP.Slot = 2
SWEP.BalanceStats = {
[TacRP.BALANCE_SBOX] = {
Damage_Max = 14,
Damage_Min = 12,
RecoilKick = 2,
},
[TacRP.BALANCE_TTT] = {
Damage_Max = 10,
Damage_Min = 8,
Range_Min = 1000,
Range_Max = 2000,
RPM = 800,
BodyDamageMultipliers = {
[HITGROUP_HEAD] = 2,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.75,
[HITGROUP_RIGHTLEG] = 0.75,
[HITGROUP_GEAR] = 0.9
},
},
[TacRP.BALANCE_PVE] = {
Damage_Max = 9,
Damage_Min = 7,
},
[TacRP.BALANCE_OLDSCHOOL] = {
RecoilSpreadPenalty = 0.0025,
RecoilMaximum = 25
}
}
SWEP.TTTReplace = TacRP.TTTReplacePreset.SMG
// "ballistics"
SWEP.Damage_Max = 15
SWEP.Damage_Min = 12
SWEP.Range_Min = 1000 // distance for which to maintain maximum damage
SWEP.Range_Max = 5000 // distance at which we drop to minimum damage
SWEP.Penetration = 10 // units of metal this weapon can penetrate
SWEP.ArmorPenetration = 0.875
SWEP.ArmorBonus = 2
SWEP.BodyDamageMultipliers = {
[HITGROUP_HEAD] = 3,
[HITGROUP_CHEST] = 1,
[HITGROUP_STOMACH] = 1.25,
[HITGROUP_LEFTARM] = 1,
[HITGROUP_RIGHTARM] = 1,
[HITGROUP_LEFTLEG] = 0.9,
[HITGROUP_RIGHTLEG] = 0.9,
[HITGROUP_GEAR] = 0.9
}
SWEP.MuzzleVelocity = 25000
// misc. shooting
SWEP.Firemodes = {
2,
1
}
SWEP.RPM = 850
SWEP.Spread = 0.006
SWEP.RecoilResetInstant = false
SWEP.RecoilPerShot = 1
SWEP.RecoilMaximum = 20
SWEP.RecoilResetTime = 0.05
SWEP.RecoilDissipationRate = 45
SWEP.RecoilFirstShotMult = 2
SWEP.RecoilVisualKick = 0.75
SWEP.RecoilKick = 1.5
SWEP.RecoilStability = 0.1
SWEP.RecoilSpreadPenalty = 0.0014
SWEP.CanBlindFire = true
// handling
SWEP.MoveSpeedMult = 0.925
SWEP.ShootingSpeedMult = 0.85
SWEP.SightedSpeedMult = 0.7
SWEP.ReloadSpeedMult = 0.5
SWEP.AimDownSightsTime = 0.35
SWEP.SprintToFireTime = 0.375
SWEP.Sway = 0.75
SWEP.ScopedSway = 0.25
SWEP.FreeAimMaxAngle = 3
// hold types
SWEP.HoldType = "smg"
SWEP.HoldTypeSprint = "passive"
SWEP.HoldTypeBlindFire = false
SWEP.GestureShoot = ACT_HL2MP_GESTURE_RANGE_ATTACK_AR2
SWEP.GestureReload = ACT_HL2MP_GESTURE_RELOAD_SMG1
SWEP.PassiveAng = Angle(0, 0, 0)
SWEP.PassivePos = Vector(0, -4, -5)
SWEP.BlindFireAng = Angle(0, 5, 0)
SWEP.BlindFirePos = Vector(0, -4, -3)
SWEP.SprintAng = Angle(30, -15, 0)
SWEP.SprintPos = Vector(5, 0, -2)
SWEP.SightAng = Angle(0.01, 0, 0)
SWEP.SightPos = Vector(-3.705, -15, -4.6)
SWEP.CorrectivePos = Vector(0.02, 0, 0.1)
SWEP.CorrectiveAng = Angle(0, 0, 0)
SWEP.HolsterVisible = true
SWEP.HolsterSlot = TacRP.HOLSTER_SLOT_BACK
SWEP.HolsterPos = Vector(5, 6, -6)
SWEP.HolsterAng = Angle(0, 0, 0)
// reload
-- Устанавливаем размер магазина и начальное кол-во патрон на 0
SWEP.ClipSize = 50
SWEP.DefaultAmmo = 0
SWEP.Ammo = "smg1"
-- Принудительное обнуление при создании (Initialize)
function SWEP:Initialize()
self.BaseClass.Initialize(self)
-- Обнуляем патроны внутри самого оружия
self:SetClip1(0)
-- Обнуляем резервные патроны у игрока через мгновение после спавна
if SERVER then
timer.Simple(0, function()
if IsValid(self) and IsValid(self:GetOwner()) then
self:GetOwner():SetAmmo(0, self:GetPrimaryAmmoType())
end
end)
end
end
SWEP.Ammo_Expanded = "ti_pdw"
SWEP.ReloadTimeMult = 1
SWEP.DropMagazineModel = "models/weapons/tacint/magazines/p90.mdl"
SWEP.DropMagazineImpact = "plastic"
SWEP.ReloadUpInTime = 1.85
SWEP.DropMagazineTime = 0.55
// sounds
local path = "tacrp/weapons/p90/"
SWEP.Sound_Shoot = "^" .. path .. "fire-1.wav"
SWEP.Sound_Shoot_Silenced = path .. "fire_silenced-1.wav"
SWEP.Vol_Shoot = 115
SWEP.ShootPitchVariance = 2.5 // amount to vary pitch by each shot
// effects
// the .qc attachment for the muzzle
SWEP.QCA_Muzzle = 1
// ditto for shell
SWEP.QCA_Eject = 2
SWEP.MuzzleEffect = "muzzleflash_smg"
SWEP.EjectEffect = 2
// anims
SWEP.AnimationTranslationTable = {
["fire_iron"] = "fire1_M",
["fire1"] = "fire1_M",
["fire2"] = "fire2_M",
["fire3"] = "fire3_M",
["fire4"] = {"fire4_M", "fire4_L", "fire4_R"},
["melee"] = {"melee1", "melee2"}
}
// attachments
SWEP.AttachmentElements = {
["optic"] = {
BGs_VM = {
{1, 1}
},
},
}
SWEP.Attachments = {
[1] = {
PrintName = "Optic",
Category = {"optic_cqb", "optic_medium"},
Bone = "p90_ROOT",
AttachSound = "tacrp/weapons/optic_on.wav",
DetachSound = "tacrp/weapons/optic_off.wav",
InstalledElements = {"optic"},
Pos_VM = Vector(-5.35, 0, 6.5),
Pos_WM = Vector(8, 1.5, -7),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -3.5, 180),
},
[2] = {
PrintName = "Muzzle",
Category = "silencer",
Bone = "p90_ROOT",
AttachSound = "tacrp/weapons/silencer_on.wav",
DetachSound = "tacrp/weapons/silencer_off.wav",
Pos_VM = Vector(-1.85, 0, 14),
Pos_WM = Vector(16, 2.25, -3.5),
Ang_VM = Angle(90, 0, 0),
Ang_WM = Angle(0, -3.5, 180),
},
[3] = {
PrintName = "Tactical",
Category = {"tactical", "tactical_zoom", "tactical_ebullet"},
Bone = "p90_ROOT",
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
InstalledElements = {"rail"},
Pos_VM = Vector(-4.35, -0.6, 7.6),
Pos_WM = Vector(10, 1.3, -4),
Ang_VM = Angle(90, 0, -90),
Ang_WM = Angle(0, -3.5, -90),
},
[4] = {
PrintName = "Accessory",
Category = {"acc", "acc_sling", "acc_duffle", "acc_extmag_smg"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
[5] = {
PrintName = "Bolt",
Category = {"bolt_automatic"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[6] = {
PrintName = "Trigger",
Category = {"trigger_auto"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[7] = {
PrintName = "Ammo",
Category = {"ammo_rifle"},
AttachSound = "TacRP/weapons/flashlight_on.wav",
DetachSound = "TacRP/weapons/flashlight_off.wav",
},
[8] = {
PrintName = "Perk",
Category = {"perk", "perk_melee", "perk_shooting", "perk_reload"},
AttachSound = "tacrp/weapons/flashlight_on.wav",
DetachSound = "tacrp/weapons/flashlight_off.wav",
},
}
local function addsound(name, spath)
sound.Add({
name = name,
channel = 16,
volume = 1.0,
sound = spath
})
end
addsound("tacint_p90.Clip_Out", path .. "clip_out.wav")
addsound("tacint_p90.Clip_In", path .. "clip_in.wav")
addsound("tacint_p90.Clip_slap", path .. "clip_slap.wav")
addsound("tacint_p90.bolt_release", path .. "bolt_release.wav")
addsound("tacint_p90.bolt_back", path .. "bolt_back.wav")
addsound("tacint_p90.bolt_forward", path .. "bolt_forward.wav")
addsound("tacint_p90.fire_select", path .. "fire_select.wav")
addsound("tacint_p90.mag_release", path .. "mag_release.wav")

Some files were not shown because too many files have changed in this diff Show More