I am making a gun, and when making the ammo code, it was being incredibly buggy. Once I unequip the gun while reloading, and equip it again, instead of subtracting ammo by 1, it subtracts it by a bigger value.

Module script (is being required by a local script):

local gunScripts = {}

gunScripts.PistolScript = function(GunName)
	local player = game.Players.LocalPlayer
	local gun = player:WaitForChild("Backpack"):WaitForChild(GunName) or player.Character:WaitForChild(GunName)
	
	function gunScripts.loadAnimation(animator, humanoid, animation)
		if not animator then
			animator = Instance.new("Animator")
			animator.Parent = humanoid
		end

		local animTrack = animator:LoadAnimation(animation)
		print(animTrack)
		return animTrack
	end
	
	--When the gun is equipped then,
	gun.Equipped:Connect(function()
		--Variables
		local runService = game:GetService("RunService")
		local UIS = game:GetService("UserInputService")
		local mouse = player:GetMouse()
		local playerGui = player:WaitForChild("PlayerGui")
		local mobileReloadGui = playerGui:WaitForChild("MobileReloadGui")
		local mobileReloadButton = mobileReloadGui:WaitForChild("ReloadButton")
		local ammoGui = playerGui:WaitForChild("AmmoGUI")
		local ammoText = ammoGui.Background.AmmoText
		local gunLabel = ammoGui.GunLabel
		local ReloadGui = playerGui:WaitForChild("ReloadGui")
		local reloadText = ReloadGui.ReloadText
		local rs = game:GetService("ReplicatedStorage")
		local re = rs:WaitForChild("Events"):WaitForChild("ShootEvent")
		local weaponInfo = require(rs.Modules.WeaponInfo)
		local gunIndex = weaponInfo:GetWeaponByName(GunName)
		local debounce = false
		local firerate = gunIndex.Firerate
		local GunAnimations = rs.GunAnimations
		local ammoAmount = gunIndex.Ammo

		local firing = false
		local reloading = false
		local char = player.Character or player.CharacterAdded:Wait()
		local hum = char:FindFirstChild("Humanoid")
		local animator = hum:FindFirstChild("Animator")
		print("equipped")
		--The display text for the gunGUI displays the gun's name.
		gunLabel.Text = gun.Name
		--Allows the player to see the ammoGUI
		ammoGui.Enabled = true
		--if ammo amount is 0 then
		if ammoAmount == 0 then
			--The player can see the reload gui
			ReloadGui.Enabled = true
		end

		--The equip animation.
		local equipAnim = GunAnimations:WaitForChild("PistolEquip")

		local equipAnimTrack = gunScripts.loadAnimation(animator, hum, equipAnim)
		equipAnimTrack.Looped = false
		equipAnimTrack:Play()
		gun:SetAttribute("PlayedEquipAnimation", false)

		equipAnimTrack.Ended:Connect(function()
			gun:SetAttribute("PlayedEquipAnimation", true)
		end)

		local holdAnim = GunAnimations:WaitForChild("PistolHold")

		local holdAnimTrack = gunScripts.loadAnimation(animator, hum, holdAnim)
		holdAnimTrack.Priority = Enum.AnimationPriority.Action
		holdAnimTrack.Looped = true
		holdAnimTrack:Play()

		--If the gun is activated, connect to a function
		mouse.Button1Down:Connect(function()
			if not firing and gun:GetAttribute("PlayedEquipAnimation") and UIS.KeyboardEnabled and not reloading then
				firing = true
				while firing == true do
					gunScripts.onActivated()
					wait(firerate)
				end
			end
		end)

		gun.Deactivated:Connect(function()
			if UIS.KeyboardEnabled then
				firing = false
			end
		end)

		UIS.InputBegan:Connect(function(input, GPE)
			if not GPE then
				if input.UserInputType == Enum.UserInputType.Touch and not UIS.KeyboardEnabled then
					if not firing and gun:GetAttribute("PlayedEquipAnimation") and not reloading then
						firing = true
						while firing == true do
							gunScripts.onActivated()
							wait(firerate)
						end
					end
				end
			end
		end)

		UIS.InputEnded:Connect(function(input, GPE)
			if not GPE then
				if input.UserInputType == Enum.UserInputType.Touch and not UIS.KeyboardEnabled then
					firing = false
				end
			end
		end)
		--When the gun is unequipped,
		gun.Unequipped:Connect(function()
			firing = false
			gun:SetAttribute("PlayedEquipAnimation", false)
			--disable the ammoGUI
			ammoGui.Enabled = false
			--disable the reloadGUI
			ReloadGui.Enabled = false
			--If the animation is still playing after the gun is unequipped,
			if equipAnimTrack.IsPlaying then
				--Stop the track
				equipAnimTrack:Stop()
				--Restart the time position.
				equipAnimTrack.TimePosition = 0
			end

			holdAnimTrack:Stop()
			holdAnimTrack.TimePosition = 0
			--Set playedequipanimation to false
			gun:SetAttribute("PlayedEquipAnimation",false)
		end)
		
		local reloadDebounce = false
		UIS.InputBegan:Connect(function(input, GPE)
			if not GPE then
				if input.KeyCode == Enum.KeyCode.R and ammoAmount < gunIndex.Ammo and gun:GetAttribute("PlayedEquipAnimation") and UIS.KeyboardEnabled and firing == false and reloadDebounce == false then
					reloadDebounce = true
					print("r pressed")
					print("passed debounce")
					
					local reloadAnim = GunAnimations:WaitForChild("PistolReload")

					local reloadTrack = gunScripts.loadAnimation(animator, hum, reloadAnim)
					reloadTrack:Play()
					local reloadSound = gun:WaitForChild("ReloadSound")
					reloadSound:Play()
				

					local isUnequipped = false
					

					gun.Unequipped:Connect(function()
						isUnequipped = true
						reloading = false
						if reloadTrack.IsPlaying then
							print("stopped")
							reloadTrack.TimePosition = 0
							reloadTrack:Stop()
							reloadSound:Stop()
							reloadDebounce = false
						end
					end)
					
					reloadTrack.Ended:Wait()
					
					if isUnequipped then return end
					
					reloading = false
					reloadDebounce = false
					ammoAmount = gunIndex.Ammo
					print("ammount = 19")
					ReloadGui.Enabled = false
					ammoGui.Background.AmmoText.Text = "Ammo: "..ammoAmount.."/"..gunIndex.Ammo
					
					--[[reloadTrack.Ended:Connect(function()
						if not isUnequipped and not firing then
							reloading = false
							reloadDebounce = false
							print("reloaded")

							ammoAmount = gunIndex.Ammo
							print("ammount = 19")
							ReloadGui.Enabled = false
						end
					end)--]]
				end
			end
		end)

		runService.Heartbeat:Connect(function()
			print(ammoAmount)
		end)

		if not UIS.KeyboardEnabled then
			gun.Equipped:Connect(function()
				if ammoAmount < gunIndex.Ammo then
					mobileReloadGui.Enabled = true
				end
			end)

			gun.Unequipped:Connect(function()
				mobileReloadGui.Enabled = false
			end)

			mobileReloadButton.MouseButton1Click:Connect(function()
				if reloadDebounce == false then
					reloadDebounce = true
					local reloadAnim = GunAnimations:WaitForChild("PistolReload")

					local reloadTrack = gunScripts.loadAnimation(animator,hum, reloadAnim)
					reloadTrack:Play()
					local reloadSound = gun:WaitForChild("ReloadSound")
					reloadSound:Play()

					local isUnequipped = false
					reloading = true

					gun.Unequipped:Connect(function()
						isUnequipped = true
						if reloadTrack.IsPlaying then
							print("stopped")
							reloadTrack.TimePosition = 0
							reloadTrack:Stop()
							reloadSound:Stop()
							reloading = false
							reloadDebounce = false
						end
					end)


					reloadTrack.Ended:Connect(function()
						if not isUnequipped or firing then
							reloading = false
							print("reloaded")

							ammoAmount = gunIndex.Ammo
							print("ammount = 19")
							ReloadGui.Enabled = false
							reloadDebounce = false
							ammoGui.Background.AmmoText.Text = "Ammo: "..ammoAmount.."/"..gunIndex.Ammo
						end
					end)
				end
			end)	
		end

		--When activated, it will fire remote event.
		function gunScripts.onActivated()
			--If the equip animation is done and if the player has more than 0 ammo then...
			if gun:GetAttribute("PlayedEquipAnimation") and ammoAmount > 0 then
				--The shooting animation for the gun.
				local shootAnim = GunAnimations.PistolShoot
				--If the character's humanoid does not have a humanoid to load animations in then: 
				local shootTrack = gunScripts.loadAnimation(animator, hum, shootAnim)
				shootTrack:Play()

				--Sets the target of the player's gun to the mouse's target.
				local params = RaycastParams.new()

				params.FilterDescendantsInstances = {
					gun,
					player.Character
				}
				params.FilterType = Enum.RaycastFilterType.Exclude
				params.IgnoreWater = true

				local mouseRay = game.Workspace.Camera:ScreenPointToRay(mouse.X, mouse.Y)
				local origin = mouseRay.Origin
				local direction = mouseRay.Direction * 500

				local result = workspace:Raycast(origin, direction, params)
				local target = nil

				if result and result.Instance then
					target = result.Instance
				end
				print(target)
				--Fires a remote event to damage the enemy.
				re:FireServer(target, result)
				--Subtracts the ammo amount variable by 1.
				ammoAmount -= 1
				--Sets the GUI text to display the amount of ammo.
				ammoGui.Background.AmmoText.Text = "Ammo: "..ammoAmount.."/"..gunIndex.Ammo
				--If the ammo amount is 0, however, then the reloadGUI displays.
				if ammoAmount == 0 then
					ReloadGui.Enabled = true
				end
			end
		end
	end)
end

return gunScripts

As always, thank you for your time.

3 comments

0

Its requiring the whole thing?

0

Why are you defining other functions inside the original one

0

what do you mean