Struggling With What To Put In Remote Event Arguments

Beginner scripter here, I’ve practiced remote events and successfully created a few remote events by now. However, as they grow more complicated and require arguments I struggle to know what actually to put in the arguments to make it function properly. I’ve read the documentation and searched the forums for code examples, but really haven’t made much progress.

Today for practice I wanted to build a turret, after finishing I decided to improve upon it. I am trying to use a client to server remote event to make the turret damage any player who is hit by the bullets coming out of it. The bulk of the code is handled by the server, I simply want the client side to handle the hit detection as I can never seem to get Players:GetPlayerFromCharacter() to work.

Server Side:

Summary

local function createBullet(player, hit)
local bullet = Instance.new(“Part”)
bullet.Size = Vector3.new(1,1,1)
bullet.Color = Color3.fromRGB(159, 161, 172)
bullet.Position = shooter.Position
bullet.Parent = workspace
bullet.CanCollide = true
bullet.CanTouch = true

for bulletVelocity = 0, 1 do
	bullet.Position += Vector3.new(10,0,0)
	wait(.1)
end

local character = Players:GetPlayerFromCharacter(player)
if bullet.Touched and character then
	character:Destroy()
end

end

local function activateTurret(player)
for turretOn = 1, BULLET_AMOUNT do
createBullet()
BULLET_COUNTER = BULLET_COUNTER + 1
print(BULLET_COUNTER… " bullets shot")
wait(SHOT_DELAY)
end
end
activate.MouseClick:Connect(activateTurret)
RE.OnServerEvent:Connect(createBullet)

Client Side

Summary

local function onServerEvent(player)

RE:FireServer(Player) -- Player = Players.LocalPlayer

end
– I have tried putting many different things in for the argument here to send local player over to the server.
Players.PlayerAdded:Connect(onServerEvent)

Please excuse the poorly written code, I am very new to scripting. Any and all feedback is appreciated, I appreciate you reading and responding. Comments written in client side code are for context.

For more context,
Output usually states “Attempt to index nil with player” when I’ve switched up the arguments

1 Like
local character = player.Character
1 Like

When a remote event is fired by the client, the first parameter is ALWAYS the player who fired it. This means that you don’t need to pass it


local character = Players:GetPlayerFromCharacter(player)

can probably just be player.Character

Still says attempting to index nil with character.

For whatever reason the server doesn’t seem to be detecting the local player

Which line is erroring?
What does your code look like?
(Put ``` before and after the code so it is formatted

Server side

local shooter = turret.Shooter
local activate = turret.Activate.ClickDetector

local ReplicatedStorage = game:GetService("ReplicatedStorage")
local RE = ReplicatedStorage:WaitForChild("DamageClient")
local Players = game:GetService("Players")
--On activate MouseButton1Click, i need the function to create a new part
-- Then have a for loop shoot multiple parts out of the turret

local BULLET_AMOUNT = 10
local BULLET_COUNTER = 0
local SHOT_DELAY = .5
--each click shoot 10 bullets with .5 seconds in between. counter counts how many have been shot

local function createBullet(player, hit)
	local bullet = Instance.new("Part")
	bullet.Size = Vector3.new(1,1,1)
	bullet.Color = Color3.fromRGB(159, 161, 172)
	bullet.Position = shooter.Position
	bullet.Parent = workspace
	bullet.CanCollide = true
	bullet.CanTouch = true
	
	
	for bulletVelocity = 0, 1 do
		bullet.Position += Vector3.new(10,0,0)
		wait(.1)
	end
	
	local plyr = Players:GetPlayerFromCharacter(player.character)
	if bullet.Touched and plyr then
		plyr:Destroy()
	end
	
end

local function activateTurret(player)
for turretOn = 1, BULLET_AMOUNT do
	createBullet()
	BULLET_COUNTER = BULLET_COUNTER + 1
	print(BULLET_COUNTER.. " bullets shot")
	wait(SHOT_DELAY)
	end
end
activate.MouseClick:Connect(activateTurret)
RE.OnServerEvent:Connect(createBullet)'''

Client side

```local ReplicatedStorage = game:GetService("ReplicatedStorage")
local RE = ReplicatedStorage:WaitForChild("DamageClient")
local Players = game:GetService("Players")
local Player = Players.LocalPlayer
local character = Player.Character


local function onServerEvent(player)
	
	RE:FireServer() 
end
-- I have tried putting many different things in for the argument here to send local player over to the server.
Players.PlayerAdded:Connect(onServerEvent)```

Server line 31 errors
attempt to index nil with "character"
1 Like

that should just be

local plyr = player

You could also just replace plyr with player wherever it occurs in the code

It still doesn’t seem to be able to find the local player.

The touch event won’t fire because of this.
I added print statements to confirm that this is the problem

You have multiple issues in your code.
First one is because you didn’t “accept” the player parameter automatically passed when a remote event is fired.

Wrong is:

RE.OnServerEvent:Connect(createBullet)

Correct for issue 1 would be:

RE.OnServerEvent:Connect(function(player)
    createBullet(player)
end)

Now we also have another issue. You are wrongfully assuming that in the definition of the “createBullet” function you can use the hit parameter.
First of all in your original code you passed nothing so this parameter couldn’t be something self defined.
Second of all you don’t use the “hit” parameter in the “createBullet” function at all.
And now to explain why you can’t use it. You are firing a remote event, passing no parameters. The hit parameter is only automatically assigned when you have a .Touched event, not speaking of the fact that it would have been the first parameter (and that would have conflicted with your player paramter).
So, just remove it and keep the player parameter.

If you still have any problems regarding this, feel free to reply.

1 Like
	local bullet = Instance.new("Part")
	bullet.Size = Vector3.new(1,1,1)
	bullet.Color = Color3.fromRGB(159, 161, 172)
	bullet.Position = shooter.Position
	bullet.Parent = workspace
	bullet.CanCollide = true
	bullet.CanTouch = true
	
	
	for bulletVelocity = 0, 1 do
		bullet.Position += Vector3.new(10,0,0)
		wait(.1)
	end
	
	
	if bullet.Touched and player then
		print("player found")
		player:Destroy()
	end
	
end

local function activateTurret(player)
for turretOn = 1, BULLET_AMOUNT do
	createBullet()
	BULLET_COUNTER = BULLET_COUNTER + 1
	print(BULLET_COUNTER.. " bullets shot")
	wait(SHOT_DELAY)
	end
end
activate.MouseClick:Connect(activateTurret)
RE.OnServerEvent:Connect(function(player)
	createBullet(player)
end)

Here is what I’ve changed, it still doesn’t seem to be detecting the player.
I fixed the function call as well as removed the hit parameter.

Yeah, you still are missing a few things.

First of all, in the for loop you also execute the “createBullet” function. Again in your original code this function expected a parameter which is required.

And second of all, in that new code, you don’t even have a “createBullet” fumction defined. Seemingly, you removed it.

You also have more issues in your code for example, in the “createBullet” function, you use the player parameter directly and later also destroy it. You can’t destroy a playerinstance in game.Players. I think you are seeking player.Character.
And to avoid unecpected behaviour, you may not destroy the character but put the Humanoids Health to 0, killing the player hit.

Also after the names of your variables, this turret seems to only affect players and not NPCs/Entities.

I made a copy paste error on my last post, I didn’t delete the entire createbullet() function. I may be a beginner but thankfully i’m not THAT beginner.

This worked, I can now find the local player and the player dies upon touching a bullet.

Thank you very much for your help man. Working through these challenges are what teach me the most! I appreciate it

No problem, keep scripting!
And don’t hesitate to ask in DevForum if you need any help.

1 Like

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.