local a=5 local z=10 local d=Random.new()local m=not IsServer and Players.LocalPlayer local Q={}Q.__index=Q setmetatable(Q,BaseWeapon)Q.CanAimDownSights=true Q.CanBeFired=true Q.CanBeReloaded=true Q.CanHit=true function Q.new(a,z)local d=BaseWeapon.new(a,z)setmetatable(d,Q)d.usesCharging=false d.charge=0 d.chargeSoundPitchMin=.5 d.chargeSoundPitchMax=1 d.triggerDisconnected=false d.startupFinished=false d.burstFiring=false d.burstIdx=0 d.nextFireTime=0 d.recoilIntensity=0 d.aimPoint=Vector3.new()d:addOptionalDescendant("\116\105\112\065\116\116\097\099\104","\084\105\112\065\116\116\097\099\104\109\101\110\116")d:addOptionalDescendant("\098\111\108\116\077\111\116\111\114","\066\111\108\116\077\111\116\111\114")d:addOptionalDescendant("\098\111\108\116\077\111\116\111\114\083\116\097\114\116","\066\111\108\116\077\111\116\111\114\083\116\097\114\116")d:addOptionalDescendant("\098\111\108\116\077\111\116\111\114\084\097\114\103\101\116","\066\111\108\116\077\111\116\111\114\084\097\114\103\101\116")d:addOptionalDescendant("\099\104\097\114\103\101\071\108\111\119\080\097\114\116","\067\104\097\114\103\101\071\108\111\119")d:addOptionalDescendant("\099\104\097\114\103\101\067\111\109\112\108\101\116\101\080\097\114\116\105\099\108\101\115","\067\104\097\114\103\101\067\111\109\112\108\101\116\101\080\097\114\116\105\099\108\101\115")d:addOptionalDescendant("\100\105\115\099\104\097\114\103\101\067\111\109\112\108\101\116\101\080\097\114\116\105\099\108\101\115","\068\105\115\099\104\097\114\103\101\067\111\109\112\108\101\116\101\080\097\114\116\105\099\108\101\115")d:addOptionalDescendant("\109\117\122\122\108\101\070\108\097\115\104\048","\077\117\122\122\108\101\070\108\097\115\104\048")d:addOptionalDescendant("\109\117\122\122\108\101\070\108\097\115\104\049","\077\117\122\122\108\101\070\108\097\115\104\049")d:addOptionalDescendant("\109\117\122\122\108\101\070\108\097\115\104\066\101\097\109","\077\117\122\122\108\101\070\108\097\115\104")d.hitMarkTemplate=HitMarksFolder:FindFirstChild(d:getConfigValue("\072\105\116\077\097\114\107\069\102\102\101\099\116","\066\117\108\108\101\116\072\111\108\101"))d.casingTemplate=CasingsFolder:FindFirstChild(d:getConfigValue("\067\097\115\105\110\103\069\102\102\101\099\116",""))d:addOptionalDescendant("\099\097\115\105\110\103\069\106\101\099\116\080\111\105\110\116","\067\097\115\105\110\103\069\106\101\099\116\080\111\105\110\116")d.ignoreList={}d.ignoreListRefreshTime=0 d:addOptionalDescendant("\104\097\110\100\065\116\116\097\099\104","\076\101\102\116\072\097\110\100\065\116\116\097\099\104\109\101\110\116")d.handAlignPos=nil d.handAlignRot=nil d.chargingParticles={}d.instance.DescendantAdded:Connect(function(a)if a.Name=="\067\104\097\114\103\105\110\103\080\097\114\116\105\099\108\101\115"and a:IsA("\080\097\114\116\105\099\108\101\069\109\105\116\116\101\114")then table.insert(d.chargingParticles,a)end end)for a,z in pairs(d.instance:GetDescendants())do if z.Name=="\067\104\097\114\103\105\110\103\080\097\114\116\105\099\108\101\115"and z:IsA("\080\097\114\116\105\099\108\101\069\109\105\116\116\101\114")then table.insert(d.chargingParticles,z)end end d:doInitialSetup()return d end function Q.onEquippedChanged(a)BaseWeapon.onEquippedChanged(a)if not IsServer then if a.weaponsSystem.camera then if a.equipped then a.startupFinished=false end end if a.equipped then ContextActionService:BindAction("\082\101\108\111\097\100\087\101\097\112\111\110",function(...)a:onReloadAction(...)end,false,Enum.KeyCode.R,Enum.KeyCode.ButtonX)else ContextActionService:UnbindAction("\082\101\108\111\097\100\087\101\097\112\111\110")local z=a:getSound("\067\104\097\114\103\105\110\103")local d=a:getSound("\068\105\115\099\104\097\114\103\105\110\103")if z and z.Playing then z:Stop()end if d and d.Playing then d:Stop()end end a.triggerDisconnected=false end end function Q.onReloadAction(m,a,z,d)if z==Enum.UserInputState.Begin and not m.reloading then m:reload()end end function Q.animateBoltAction(z,a)if not z.boltMotor or not z.boltMotorStart or not z.boltMotorTarget then return end if a then z:tryPlaySound("\066\111\108\116\079\112\101\110\083\111\117\110\100")else z:tryPlaySound("\066\111\108\116\067\108\111\115\101\083\111\117\110\100")end local d=a and z:getConfigValue("\065\099\116\105\111\110\079\112\101\110\084\105\109\101",.025)or z:getConfigValue("\065\099\116\105\111\110\067\108\111\115\101\084\105\109\101",.075)local m=a and z.boltMotorTarget.CFrame or z.boltMotorStart.CFrame local Q=TweenService:Create(z.boltMotor,TweenInfo.new(d,Enum.EasingStyle.Quad,Enum.EasingDirection.InOut),{C0=m})Q:Play()Q.Completed:Wait()end function Q.getRandomSeedForId(z,a)return a end

local IGNORE_LIST_LIFETIME = 5

local MAX_BULLET_TIME = 10

local localRandom = Random.new()
local localPlayer = not IsServer and Players.LocalPlayer

local BulletWeapon = {}
BulletWeapon.__index = BulletWeapon
setmetatable(BulletWeapon, BaseWeapon)

BulletWeapon.CanAimDownSights = true
BulletWeapon.CanBeFired = true
BulletWeapon.CanBeReloaded = true
BulletWeapon.CanHit = true

function BulletWeapon.new(weaponsSystem, instance)
	local self = BaseWeapon.new(weaponsSystem, instance)
	setmetatable(self, BulletWeapon)

	self.usesCharging = false
	self.charge = 0
	self.chargeSoundPitchMin = 0.5
	self.chargeSoundPitchMax = 1

	self.triggerDisconnected = false
	self.startupFinished = false -- TODO: make startup time use a configuration value
	self.burstFiring = false
	self.burstIdx = 0
	self.nextFireTime = 0

	self.recoilIntensity = 0
	self.aimPoint = Vector3.new()

	self:addOptionalDescendant("tipAttach", "TipAttachment")

	self:addOptionalDescendant("boltMotor", "BoltMotor")
	self:addOptionalDescendant("boltMotorStart", "BoltMotorStart")
	self:addOptionalDescendant("boltMotorTarget", "BoltMotorTarget")

	self:addOptionalDescendant("chargeGlowPart", "ChargeGlow")
	self:addOptionalDescendant("chargeCompleteParticles", "ChargeCompleteParticles")
	self:addOptionalDescendant("dischargeCompleteParticles", "DischargeCompleteParticles")

	self:addOptionalDescendant("muzzleFlash0", "MuzzleFlash0")
	self:addOptionalDescendant("muzzleFlash1", "MuzzleFlash1")
	self:addOptionalDescendant("muzzleFlashBeam", "MuzzleFlash")

	self.hitMarkTemplate = HitMarksFolder:FindFirstChild(self:getConfigValue("HitMarkEffect", "BulletHole"))

	self.casingTemplate = CasingsFolder:FindFirstChild(self:getConfigValue("CasingEffect", ""))
	self:addOptionalDescendant("casingEjectPoint", "CasingEjectPoint")

	self.ignoreList = {}
	self.ignoreListRefreshTime = 0

	self:addOptionalDescendant("handAttach", "LeftHandAttachment")
	self.handAlignPos = nil
	self.handAlignRot = nil

	self.chargingParticles = {}
	self.instance.DescendantAdded:Connect(function(descendant)
		if descendant.Name == "ChargingParticles" and descendant:IsA("ParticleEmitter") then
			table.insert(self.chargingParticles, descendant)
		end
	end)
	for _, v in pairs(self.instance:GetDescendants()) do
		if v.Name == "ChargingParticles" and v:IsA("ParticleEmitter") then
			table.insert(self.chargingParticles, v)
		end
	end

	self:doInitialSetup()

	return self
end

function BulletWeapon:onEquippedChanged()
	BaseWeapon.onEquippedChanged(self)

	if not IsServer then
		if self.weaponsSystem.camera then
			if self.equipped then
				self.startupFinished = false
			end
		end

		if self.equipped then
			ContextActionService:BindAction("ReloadWeapon", function(...) self:onReloadAction(...) end, false, Enum.KeyCode.R, Enum.KeyCode.ButtonX)
		else
			ContextActionService:UnbindAction("ReloadWeapon")

			-- Stop charging/discharging sounds
			local chargingSound = self:getSound("Charging")
			local dischargingSound = self:getSound("Discharging")
			if chargingSound and chargingSound.Playing then
				chargingSound:Stop()
			end
			if dischargingSound and dischargingSound.Playing then
				dischargingSound:Stop()
			end
		end

		self.triggerDisconnected = false
	end
end

function BulletWeapon:onReloadAction(actionName, inputState, inputObj)
	if inputState == Enum.UserInputState.Begin and not self.reloading then
		self:reload()
	end
end

function BulletWeapon:animateBoltAction(isOpen)
	if not self.boltMotor or not self.boltMotorStart or not self.boltMotorTarget then
		return
	end

	if isOpen then
		self:tryPlaySound("BoltOpenSound")
	else
		self:tryPlaySound("BoltCloseSound")
	end

	local actionMoveTime = isOpen and self:getConfigValue("ActionOpenTime", 0.025) or self:getConfigValue("ActionCloseTime", 0.075)
	local targetCFrame = isOpen and self.boltMotorTarget.CFrame or self.boltMotorStart.CFrame

	local boltTween = TweenService:Create(self.boltMotor, TweenInfo.new(actionMoveTime, Enum.EasingStyle.Quad, Enum.EasingDirection.InOut), { C0 = targetCFrame })
	boltTween:Play()
	boltTween.Completed:Wait()
end

function BulletWeapon:getRandomSeedForId(id)
	return id
end
