I am currently building a Nerf Gun FPS. I am currently struggling with communication between server and client. My goal is to spawn a dart using a server script and remote functions. Script is below:
--Main Script which goes in Server Storage --
local serverStorage = game:GetService("ServerStorage")
local replicatedStorage = game:GetService("ReplicatedStorage")
local KOValue = "Kills"
local WOValue = "Wipeouts"
local damage = 30
replicatedStorage.ShootEvent.OnServerEvent:Connect(function(player,tool,position,part)
if game.Workspace[player.Name].Humanoid.Health <= 0 then
-- The player is dead, do not do anything
else
-- Create a clone of Dart and set its color
local Dart =
local dartClone = Dart:Clone()
--game.Debris:AddItem(dartClone, 30)
dartClone.BrickColor = player.TeamColor
dartClone.Touched:connect(function(hit)
if hit and hit.Parent and hit.Parent ~= player.Character and hit.Parent ~= tool then
dartClone:Destroy()
end
end)
spawn(function()
wait(30)
if dartClone then dartClone:Destroy() end
end)
-- Position the dart clone and launch!
local spawnPosition = (tool.Handle.CFrame * CFrame.new(2, 0, 0)).p
dartClone.CFrame = CFrame.new(spawnPosition, target) --NOTE: This must be done before assigning Parent
dartClone.Velocity = dartClone.CFrame.lookVector * dartspeed --NOTE: This should be done before assigning Parent
dartClone.Parent = game.Workspace
-- Attach creator tags to the dart early on
local creatorTag = Instance.new('ObjectValue', dartClone)
creatorTag.Value = player
creatorTag.Name = 'creator' --NOTE: Must be called 'creator' for website stats
local iconTag = Instance.new('StringValue', creatorTag)
iconTag.Value = tool.TextureId
iconTag.Name = 'icon'
delay(delay, function()
end)
if part then
if part.Name == "Head" or part:IsA("Hat") and part.Parent:FindFirstChild("Humanoid").Health > 0 then
-- Boom headshot
replicatedStorage.Headshot:FireClient(player)
damage = 1000
return "Headshot!"
end
local humanoid = part.Parent:FindFirstChild("Humanoid")
if not humanoid then
humanoid = part.Parent.Parent:FindFirstChild("Humanoid")
else
humanoid:TakeDamage(damage)
if humanoid.Health <= 0 then
player.leaderstats[KOValue].Value = player.leaderstats[KOValue].Value + 1
game.Players[humanoid.Parent.Name].leaderstats[WOValue].Value = game.Players[humanoid.Parent.Name].leaderstats[WOValue].Value + 1
end
end
wait(30)
if dartClone then
dartClone:Destroy()
end
end
end
end)
replicatedStorage.EquipAnimation.OnServerEvent:Connect(function(player,animation)
local newAnim = game.Workspace[player.Name].Humanoid:LoadAnimation(animation)
newAnim:Play()
replicatedStorage.UnequipAnimation.OnServerEvent:Connect(function(player,animation)
newAnim:Stop()
for i,v in pairs(game.Workspace:GetChildren()) do
if v.Name == player.Name.."'s Trajectory" then
v:Destroy()
end
end
end)
replicatedStorage.Reload.OnServerEvent:Connect(function(player,animation)
newAnim:Stop()
local reloadAnim = game.Workspace[player.Name].Humanoid:LoadAnimation(animation)
reloadAnim:Play()
end)
end)
Local Script Below:
--Constraints
local IgnoreList = {rocket = 0, handle = 1, effect = 1, water = 1} -- Rocket will fly through things named these
--NOTE: Keys must be lowercase, values must evaluate to true
--Variables
local tool = script.Parent
local player = game.GetService("Players").LocalPlayer
local mouse = player:GetMouse()
local gungui = tool:WaitForChild("GunGUI" )
local firesound = tool.WaitForChild("FireSound")
local reloadsound = tool.WaitForChild("ReloadSound")
local primesound = tool.WaitForChild("PrimeSound")
local primedelay = tool.Configurations:WaitForChild("PrimeDelay")
local damage = tool.Configurations:WaitForChild("Damage")
local range = tool.Configurations:WaitForChild("Range")
local dartspeed = tool.Configurations:WaitForChild("DartSpeed") -- Speed of the projectile
local reloadtime = tool.Configurations:WaitForChild("ReloadTime") -- Seconds until tool can be used again
local primingtime = tool.Configurations:WaitForChild("PrimeTime") --seconds until tool can be used again
local torso = nil
local reloading = false --reloading check
local priming = false -- priming check
local capacity = tool:WaitForChild("Capacity")
local CreatorTag = Dart:WaitForChild('creator', 60)
local gravityacceleration = 196.2
local dartmeshid = 'rbxassetid://2906043627'
local meshscale = Vector3.new(0.17,0.17,.25)
local dartpartscale = Vector3.new(1, 1, 1)
local dartcolor = BrickColor.new(33, 60, 122)
local dartscript = script:WaitForChild('Dart')
--local contextActionService = game:GetService("ContextActionService")
--caters to mobile gamers (A Later Update)
local bodytype = nil
local difference = 0 -- dif between head and mouse
local replicatedstorage = game.GetService("ReplicatedStorag")
local gungui = tool:WaitForChild("GunGUI")
--remote events
local equipAnimation = replicatedstorage:WaitForChild("EquipAnimation")
local unequipanimation = replicatedstorage:WaitForChild("UnequipAnimation")
local primeAnimation = replicatedstorage:WaitForChild("PrimeAnimation")
local shootevent = replicatedstorage:WaitForChild("ShootEvent")
local prime = replicatedstorage:WaitForChild("Prime")
local reload = replicatedstorage:WaitForChild("Reload")
local headshot = replicatedstorage:WaitForChild("Headshot")
--remote functions
local checkBodyType = replicatedstorage:WaitForChild("CheckBodyType")
local fetchRemainingAmmo = replicatedstorage:WaitForChild("FetchRemainingAmmo")
--bodytype
function findBodyType()
bodytype = checkBodyType:InvokeServe(tool)
print(bodytype)
end
--When tool is equipped this script will run
local function OnTouched(otherPart)
if Dart and otherPart then
-- Fly through anything in the ignore list
if IgnoreList[string.lower(otherPart.Name)] then
return
end
tool.Equipped:Connect(function(mouse)
gungui:Clone().Parent = player.PlayerGui -- cloning gui into player on equip
findBodyType() -- not used
equipAnimation:FireServer(tool.shoot) -- calling remote event to add to server equip animation
mouse.Icon = ""
--shoot function
mouse.Button1Down:Connect(function()
if Capacity <=0 or reloading == true or priming == true or cooldown == true then
--do nothing
else
local head = game.Workspace [player.Name].Head.CFrame.lookVector
local mouse = CFrame.new(game.Workspace[player.Name].Head.Position,mouse.Hit.p).lookVector
difference = (head-mouse)
local
--DartHERE-----------------
local function OnActivated()
local myModel = player.Character
if Tool.Enabled and myModel and myModel:FindFirstChild('Humanoid') and myModel.Humanoid.Health > 0 then
Tool.Enabled = false
game.ReplicatedStorage.ROBLOX_RocketFireEvent:FireServer(mouse.Hit.p)
wait(2)
Tool.Enabled = true
if humanoid and humanoid.Health > 0 then -- Humanoids are tagged and damaged
if hitPart.Name == 'Torso' then
ApplyTags(humanoid)
humanoid:TakeDamage(100)
end
end
end
end
local function OnTouched(otherPart)
if Dart and otherPart then
-- Fly through anything in the ignore list
if IgnoreList[string.lower(otherPart.Name)] then
return
end
local myPlayer = CreatorTag.Value
if myPlayer then
-- Fly through the creator
if myPlayer.Character and myPlayer.Character:IsAncestorOf(otherPart) then
return
end
-- Fly through friendlies
if not myPlayer.Neutral then
local character = FindCharacterAncestor(otherPart.Parent)
local player = PlayersService:GetPlayerFromCharacter(character)
if player and player ~= myPlayer and player.TeamColor == Dart.BrickColor then
return
end
end
end
-- Fly through terrain water
if otherPart == game.Workspace.Terrain then
--NOTE: If the Dart is large, then the simplifications made here will cause it to fly through terrain in some cases
local frontOfRocket = Dart.Position + (Dart.CFrame.lookVector * (Dart.Size.Z / 2))
local cellLocation = game.Workspace.Terrain:WorldToCellPreferSolid(frontOfRocket)
local cellMaterial = game.Workspace.Terrain:GetCell(cellLocation.X, cellLocation.Y, cellLocation.Z)
if cellMaterial == Enum.CellMaterial.Water or cellMaterial == Enum.CellMaterial.Empty then
return
end
end
-- Connect custom logic for the explosion
explosion.Hit:connect(function(hitPart, hitDistance) OnExplosionHit(hitPart, hitDistance, explosion.Position) end)
-- Move this script and the creator tag (so our custom logic can execute), then destroy the Dart
CreatorTag.Parent = script
Dart:Destroy()
end
end
Dart.Touched:connect(OnTouched)
if difference.magnitude < 1.33 then
shootevent:FireServer(tool,position,part)
Capacity.Value = Capacity.Value - 1

5 comments
Server scripts should go into ServerScriptService, and the remote events inside of ReplicatedStorage.
Please specify your issue and where the issue is in your code. Honestly, nobody feels like trying to understand over 200 lines of another person's unknown code without understanding what the issue even is exactly.
I didn't think so
My problem is this. I had an original script that simply fired the dart. I used a few YT vids to make it create remote functions on tool equip but It didn't do much else. Recently I have tried to rewrite the script and add some animations and a HUD, but the original script is confusing me.
Originally I had a local script that I copied from somewhere that made the tool mobile compatible, and the setup was a Script inside of a Local script with no server scripts. I've never been good with scripting tools, but online it said to use Remote Functions and Server scripts. In the server script on lines 14 - 47 I have the main dart mesh. I'm confused on where to put it.