Is there really a difference? Or can I place them interchangeably?
StarterCharacterScripts are placed in the Players Character, this could mean that the script resets on the players death because it copies the script over to the newly generated character (if that makes sense)
StarterPlayerScripts are placed in the Player, the same place where the PlayerGUI is stored. This means that it persists even when the player dies.
The main differences come down to this:
StarterChararacterScripts
-
These are cloned into the Player’s
Character
every time they respawn.- This means that once a Character respawns, a new version of that script will be cloned into the Character model and it’ll restart from the beginning of the code.
StarterPlayerScripts
-
These are cloned one time, when the player first joins the game, and are placed into the Player’s
PlayerScripts
folder.-
Importantly, Server
Scripts
will not run when placed into thePlayerScripts
folder. This means that if you place any scripts into theStarterPlayerScripts
container, it should be aLocalScript
. -
Also, the server does not have access to viewing the contents of the
PlayerScripts
folder, so it cannot forcefully delete aLocalScript
without communicating that request to the client via something like aRemoteEvent
.
-
Main Takeaway / TL;DR
- If you want to run code that specifically affects the Player’s
Character
, and are certain that it will continue working as expected even though the Script will restart from the very beginning every time the player’s Character respawns, then you can place it into theStarterChararacterScripts
.
- If you want to run client-sided code that isn’t solely related to the player’s Character, and / or if it doesn’t make much sense being placed into the
Character
or aScreenGui
, then you can place it into theStarterPlayerScripts
. However, this is a generalization; you can still useLocalScripts
to handle Character-related functions, even if thatLocalScript
is not placed in the Character model.
Examples / Situations for why you might use one over the other
-
If you want the code within a
LocalScript
to continue running without interruptions, even when a player’sCharacter
respawns, it would be better suited forStarterPlayerScripts
.- For example, if you wanted to handle something such as player input (detecting when a player presses a specific button on their keyboard, controller, or a touch-screen action), it would make more sense for that to reside in the
PlayerScripts
folder so that it doesn’t have to restart what it’s doing every time the player’s Character respawns. Example:
- For example, if you wanted to handle something such as player input (detecting when a player presses a specific button on their keyboard, controller, or a touch-screen action), it would make more sense for that to reside in the
-- Example: LocalScript placed into StarterPlayerScripts
local UserInputService = game:GetService("UserInputService")
UserInputService.InputBegan:Connect(function(inputObject)
local userInputType = inputObject.UserInputType
local keyCode = inputObject.KeyCode
print("The player used: "..userInputType.Name)
if keyCode ~= Enum.KeyCode.Unknown then
warn("And the player pressed: "..keyCode.Name)
end
--[[ You could utilize this to perform some sort of action if the player
presses a specific keybind. Even if that action is meant to affect
the player's Character model in some way, it makes more sense to have this
code running from here so that it doesn't suddenly stop running the moment
the player's Character respawns
--]]
end)
-
Although keep in mind that if you decide to reference the player’s
Character
via aLocalScript
that was cloned into thePlayerScripts
folder, you would need to make sure that you update any variables for the player’s Character and its descendants, or else it may continue referring to an older version of their Character and not the newest one that has respawned.Here’s an example
LocalScript
that you can place into theStarterPlayerScripts
, start a playtest in Roblox Studio, and then view the Output to see what happens:
-- Example: LocalScript placed into StarterPlayerScripts
local Players = game:GetService("Players")
local player = Players.LocalPlayer
local currentNumber = 1
local Character = player.Character or player.CharacterAdded:Wait()
Character:SetAttribute("CharacterNumber", currentNumber)
print("Initial Character was assigned the value of: "..tostring(Character:GetAttribute("CharacterNumber") ) )
player.CharacterAdded:Connect(function(newCharacter)
currentNumber += 1
newCharacter:SetAttribute("CharacterNumber", currentNumber)
print("A new Character has spawned!")
warn("newCharacter was assigned the value of: "..tostring(newCharacter:GetAttribute("CharacterNumber") ) )
print("Now, let's reference the original Character variable...")
warn("The value assigned to the Character stored within the original variable is: "..tostring(Character:GetAttribute("CharacterNumber") ) )
--[[ This second warning will ALWAYS print the initial number because the
original Character variable was never updated to reflect the Character that
had most recently respawned.
However, if you added the following line of code into this function:
Character = newCharacter
Then what would happen is that the original "Character" variable
will be updated to reference the Character that just spawned.
--]]
end)
while true do
task.wait(8)
local currentCharacter = player.Character or player.CharacterAdded:Wait()
local Humanoid = currentCharacter:WaitForChild("Humanoid", 5)
if currentCharacter and Humanoid then
Humanoid.Health = 0
end
end
-
If you want something to specifically affect the player’s
Character
model, such as handling health regeneration or animations, that would make more sense to be placed in theStarterChararacterScripts
.Because a new version of the script is cloned into the Character model immediately upon respawn, the code will be able to instantly reference the newest Character model without needing to worry about listening for
Player.CharacterAdded
to fire, updating old variables that referred to the previous Character model, and so on. Here’s an example:
-- Example: LocalScript or Script placed into StarterCharacterScripts
local currentTime = os.date()
warn("This code has just started running at the following time: "..currentTime)
local Character = script.Parent
local Humanoid = Character:WaitForChild("Humanoid")
print("Activating superpowers!")
Humanoid.WalkSpeed = 50
Humanoid.JumpHeight = 20
task.wait(10)
Humanoid.Health = 0
print("The Character is about to respawn...")
Basically, cloning Scripts into the Character model upon respawn (which is being handled by the StarterCharacterScripts
without needing to write any extra code to do that) simplifies the process of making sure that any code you’ve written that is meant to affect the player’s Character is actually referencing the current version of the player’s Character.
-
In fact, this is already how the default health regeneration functionality / animations are handled by Roblox. If you open up a brand new baseplate template in Roblox Studio, start a playtest, and then open the Character model within the explorer, you’ll see a “Health”
Script
and an “Animate”LocalScript
.If you want to replace any of the default
Scripts
orLocalScripts
within theCharacter
, you can place a script intoStarterChararacterScripts
that has the exact name of “Health” or “Animate”, and it’ll use the one that you created instead of the default one.
I could probably explain a whole lot more about this, but I think this should be sufficient enough for now
If you have any further questions, feel free to ask and I’ll respond when I am next available (I haven’t gone to sleep yet and it is 7 AM; I just realized I have spent the past hour and a half writing this, but it was worth it!! More knowledge to go around )
It definitely was.
Thank you so much for the simple explanation! I highly appreciate it!
This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.