Hey guys I have this basic weapon system that I made in a blank game so that I could implement it in my actual game later. It's very basic and pretty much just shows the concept of what I want. I was wondering if there was something I could change to make it a better system?

Everything works but I just want to make it as good as possible. I have not done exploit checks yet, this is only about organization.

Thanks for taking the time to review.

The Server Script in ServerScriptService

local Module = require(game.ReplicatedStorage.WeaponSystem)
local ShootBullet = game.ReplicatedStorage.RemoteFunction2
local SetAmmo = game.ReplicatedStorage.RemoteFunction

playerData = {}

-- Adds player to the playerData table. Save the players stats table when removed.
game.Players.PlayerAdded:Connect(function(player)
	playerData[""..player.UserId] = {
	
		-- Obviously I would get the stats from the datastore and update them.
		-- PlacedIn would be an array that increments the index what they placed in.
		Stats = {
			PlacedIn = nil,
			Kills = nil,
			Deaths = nil,
			LongShotsWithWeapons = nil,
			--etc...
		},
		
		-- This would be the same everytime. 
		InGame = {
			Health = 100,
			MaxHealth = 100,
			Armor = 0,
			Ammo = 0,
			MaxAmmo = 0,
			Weapons = {}
		}
	}
end)

-- This would Bullet Data to clients so they can create the bullet themselves.
-- Also updates ammo values for player.
-- No exploit checks yet.
ShootBullet.OnServerInvoke = function(player, Weapon)
	playerData[""..player.UserId].InGame.Ammo = playerData[""..player.UserId].InGame.Ammo - 1
	Weapon.WeaponData.Ammo = playerData[""..player.UserId].InGame.Ammo
	
	return Weapon.WeaponData
end

-- Just sets the ammo on weapon equip or something.
SetAmmo.OnServerInvoke = function(player, Weapon)
	local t = {
		Ammo = playerData[""..player.UserId].InGame.Ammo,
		MaxAmmo = playerData[""..player.UserId].InGame.MaxAmmo,
	}
	return t
end

The module script in replicated storage:

local RunService = game:GetService("RunService")
local ShootBullet = game.ReplicatedStorage.RemoteFunction2
local SetAmmo = game.ReplicatedStorage.RemoteFunction


-- New Weapons table for every players data table.
local Weapon = {}

Weapon.__index = Weapon

-- Set the ammo for the weapon
function Weapon:SetAmmo()
	-- Checks if it's running on the client. Maybe NPCs are firing something.
	if RunService:IsClient() then
		self.WeaponData =  SetAmmo:InvokeServer(self)
	end
end

-- Sets the Weapon.WeaponData to new values
function Weapon:ShootBullet()
	if RunService:IsClient() then
		self.WeaponData = ShootBullet:InvokeServer(self)
	end
end

-- Creates a new child of Weapon.
function Weapon:New()
	local t = setmetatable({}, self)
	return t
end

return Weapon

The local script inside a tool

local Module = require(game.ReplicatedStorage.WeaponSystem)
local player = game.Players.LocalPlayer

-- Fired when weapon is picked up or something.
local Weapon = Module:New()
Weapon.Owner = player

-- When equipped
Weapon:SetAmmo()
-- Fired when player clicks to shoot
Weapon:ShootBullet()

1 comment

0

Also setAmmo would actually be more like set weapon, and it would search through a table for the weapons data. Like damage and all of that.