I have been trying to work on a Region3 script were when you are in it, it plays a song. But I've come across 2 issues, 1 being it thinks the player is always in it when you the player isn't. And the second being the script runs so fast that it keeps repeating before anything can happen
local RegionPart = game.Workspace.RegionArea
local pos1 = RegionPart.Position - (RegionPart.Size / 2)
local pos2 = RegionPart.Position + (RegionPart.Size / 2)
local Region = Region3.new(pos1, pos2)
while true do
wait()
local burhj = workspace:FindPartsInRegion3(Region, nil, 1000)
local song = game.Workspace.bb
song:Play()
print("THE SCRIPT WORKS!")
end
You query the objects which are in Region, but never used the result and just continued. Loop over burhj and check for valid parts.
In this forum the use of FindFirstChild is suggested:
for i,v in ipairs(burhj) do
local player = v.Parent:FindFirstChild("Humanoid")
if player then
print("player is in region: " + player.Parent.Name)
end
end
Alternatively, you can directly use the player position, if the player object or position is known:
local pos = yourPlayer.HumanoidRootPart.Position
local center = region.CFrame
local size = region.Size
if pos.X > center.X - size.X / 2 and pos.X < center.X + size.X / 2 and ... then
print("player is in region")
end
A helper function, if not already present, might be helpful.
For the second problem, set a flag if the player is in the region. Play the sound when the flag was not already set. Unset the flag if you leave the region.
--here are your vars
local enteredFlag = false
while true do
wait()
if playerIsWithinRegion then --here come whatever approach you chose earlier
if not enteredFlag then
enteredFlag = true
local song = game.Workspace.bb
song:Play()
print("THE SCRIPT WORKS!")
end
else
--no player is in the region, lets reset the flag
enteredFlag = false
end
end
Related
local player = game.Players.LocalPlayer
local mouse = player:GetMouse()
local mutebutton = script.Parent
local track = game.StarterGui.MusicPlayer.Track
local b = game.StarterGui.MusicPlayer.Playlist:GetChildren()
local c = math.random(1, #b)
local d = b[c]
while true do
wait()
d:Play()
local connection = mutebutton.MouseButton1Click:Connect(function()
if d.IsPaused then
d:Resume()
mutebutton.Text = "Pause"
else
d:Pause()
mutebutton.Text = "Resume"
end
end)
d.Ended:Wait()
connection:Disconnect()
d:GetPropertyChangedSignal("SoundId"):Connect(function()
track.Text = d.Name
end)
end
Everything works until the Get Property Changed Signal event. Whenever I load into the game the box that should have the song name will instead not do anything and keep it as an empty box. Anyone know why?
It seems you have a single mute button (not one for each song), so why are you putting the pausing functionality inside a while loop?
You're not changing the sound id anywhere, is there more code that you're not showing?
You have a variable "local d" but this is only ever calculated outside of the loop so it will just repeat the same song over.
local player = game.Players.LocalPlayer
local mouse = player:GetMouse()
local mutebutton = script.Parent
local track = game.StarterGui.MusicPlayer.Track
local b = game.StarterGui.MusicPlayer.Playlist:GetChildren()
local c = math.random(1, #b)
local song -- definite it originally here as nil so we can access it outside of the loop
mutebutton.MouseButton1Click:Connect(function()
if song.IsPaused then
song:Resume()
mutebutton.Text = "Pause"
else
song:Pause()
mutebutton.Text = "Resume"
end
end)
while true do
song = b[math.random(1, #b)]
track.Text = song.Name
song:Play()
song.Ended:Wait()
task.wait()
end
This might work, but I can't see your Explorer
I'm trying to make a procedurally generating game (ignore the goal of the game).
Currently I'm trying to make it so when you walk over a grid piece and collide with an invisible part it makes that specific grid piece the Current Global Object (CGO).
Using a BoolValue I made it possible to use this as some form of global variable, but whenever I try to use said value it only detects it as false even when it is indeed showing as true in the Explorer. It only works when I set the value to true BEFORE testing the game.
Here's the code in the script that's meant to detect the value:
it's a regular script and not a LocalScript fyi
local CGO = "0,0"
local tracker = game.Workspace.Tracker00
--local CGOa = tracker.CGOa
local trackerPos = tracker.Position
local trackerX = trackerPos.X
local trackerY = trackerPos.Y
local trackerZ = trackerPos.Z
while true do
while tracker.CGOa.Value == false do
tracker.YVal.Value = 7
print("Set TrackerYVal to 7")
wait()
if tracker.CGOa.Value == true then
break
end
end
while tracker.CGOa.Value == true do
tracker.YVal.Value = 14
print("Set TrackerYVal to 14")
wait()
end
tracker.CFrame = CFrame.new(trackerX, trackerY, trackerZ)
wait()
end
Any help would be much appreciated.
Rather than using infinite while loops, consider listening for the Changed signal. It's possible that the break command might be escaping both loops.
local tracker = game.Workspace.Tracker00
tracker.CGOa.Changed:Connect(function(newVal)
print("CGOa changed to ", newVal)
if newVal then
tracker.YVal.Value = 14
print("Set TrackerYVal to 14")
else
tracker.YVal.Value = 7
print("Set TrackerYVal to 7")
end
-- update the tracker position based on newly updated values
local x = tracker.XVal.Value
local y = tracker.YVal.Value
local x = tracker.ZVal.Value
tracker.CFrame = CFrame.new(Vector3.new(x, y, z))
end)
I made some assumptions about how you were positioning the tracker, because the old code would reset its position after every loop.
So, I have a game on Roblox currently in development, and I am trying to make a coin counter. Basically, when the coin is collected, a NumberValue in StarterPlayer changes by +1. Then, A TextLabel will loop to check the value of the NumberValue. It will then change the text to display the value of the NumberValue.
However, when I playtest, nothing happens. The counter doesn't change, but the NumberValue does.
Here's the code for the Coin:
local coin = script.Parent
local sp = game:GetService("StarterPlayer")
local count = sp.Coins
local p = game:GetService("Players")
local Touched = false
coin.Touched:Connect(function()
count.Value += 1
local Sparkles = Instance.new("Sparkles")
Sparkles.Parent = coin
Sparkles.SparkleColor = Color3.fromRGB(255, 255, 0)
wait(2)
count.Value += 1
coin:Destroy()
end)
And the code for the TextLabel:
local StarterPlayer = game:GetService("StarterPlayer")
local Coins = StarterPlayer.Coins
local CoinLabel = script.Parent
while true do
CoinLabel.Text = Coins.Value
end
Does anyone know how to fix this?
The reason why your TextLabel is never updating is because you have an infinite loop that causes the script to timeout and stop running.
while true do
CoinLabel.Text = Coins.Value
end
The simple fix for that is to only update the TextLabel when the NumberValue changes :
Coins.Changed:Connect(function()
CoinLabel.Text = Coins.Value
end)
But something else is a little weird too. Objects in StarterPlayer are expected to be copied to each player when they join, but StarterPlayer.Coins is not, and as it is right now, it is acting as a global counter for everyone. So your code is modifying the Coins object that would be copied over to new players, not the one that each player has.
But according to the documentation for StarterPlayer, only a few kinds of objects in StarterPlayer are copied to players.
A StarterPlayerScripts instance, with scripts that run once for each player.
A StarterCharacterScripts instance, with scripts to add to each player’s character every time they spawn.
A Humanoid instance named StarterHumanoid, which will be used as the default humanoid for each player’s character.
A Model instance named StarterCharacter, which will be used as the character model for all players
So the NumberValue wouldn't have been copied to each player even if this logic was set up to locate it properly! So, we need to make a few changes :
A Coins NumberValue needs to be created for each player when they join the game.
You need to update the paths to the individual Coins NumberValues for each player.
Your TextLabel code should listen for the
NumberValue.Changed
signal, that way your TextLabel will only update when the
NumberValue does.
So in a Script somewhere like ServerScriptService, add this to create a Coins NumberValue for each Player :
local Players = game:GetService("Players")
Players.PlayerAdded:Connect(function(player)
-- give each player a Coins object
local coins = Instance.new("NumberValue")
coins.Name = "Coins"
coins.Value = 0
coins.Parent = player
end)
Next, update the paths in each script to reflect the new location of the object. In the first script, use the player that touched the coin to locate the Player object :
local coin = script.Parent
local Players = game:GetService("Players")
local Touched = false
coin.Touched:Connect(function(otherPart)
-- make sure a player touched this
if otherPart.Parent:FindFirstChild("Humanoid") == nil then
return
end
-- only call this function once
if Touched then
return
end
Touched = true
-- get the player
local player = Players:GetPlayerFromCharacter(otherPart.Parent)
if not player then
return
end
-- increment the player's coin counter
player.Coins.Value += 1
-- show some sparkles
local Sparkles = Instance.new("Sparkles")
Sparkles.SparkleColor = Color3.fromRGB(255, 255, 0)
Sparkles.Parent = coin
-- destroy the coin after a moment
wait(2)
coin:Destroy()
end)
Finally, update the LocalScript that updates the TextLabel so that it properly finds the NumberValue and updates only when the NumberValue changes :
local Players = game:GetService("Players")
local player = Players.LocalPlayer
local Coins = player.Coins
local CoinLabel = script.Parent
Coins.Changed:Connect(function()
CoinLabel.Text = Coins.Value
end)
I am trying to make the players max zoom distance more depending on the powr (strength) they have, because the more strength the bigger the character is.
But I'm getting the above error:
attempt to index nil with 'CameraMaxZoomDistance'
Here is my code:
hum:WaitForChild("BodyDepthScale").Value = .5 + (powr.Value / 250)
hum:WaitForChild("BodyHeightScale").Value = .5 + (powr.Value / 250)
hum:WaitForChild("BodyWidthScale").Value = .5 + (powr.Value / 250)
hum:WaitForChild("HeadScale").Value = .5 + (powr.Value / 250)
if powr.Value > 1000 then
game:GetService("Players").LocalPlayer.CameraMaxZoomDistance = powr.Value / 50
end
if powr.Value > 200 then
print('higher')
hum.MaxHealth = powr.Value / 2
end
Your error is saying that game:GetService("Players").LocalPlayer is nil. According to the docs for LocalPlayer :
This property is only defined for LocalScripts (and ModuleScripts required by them), as they run on the client. For the server (on which Script objects run their code), this property is nil.
You're trying to access the Player object for a specific character model, and there are a few different ways to get it. You already have access to the humanoid object, which is in the character model itself, so I would recommend using the Players:GetPlayerFromCharacter function to locate the Player object.
if powr.Value > 1000 then
-- get the character model
local character = hum.Parent
-- lookup the player based on the character
local PlayerService = game:GetService("Players")
local player = PlayerService:GetPlayerFromCharacter(character)
if not player then
warn("Could not locate player from character : ", character.Name)
return
end
-- adjust the player's camera zoom distance
player.CameraMaxZoomDistance = powr.Value / 50
end
I have this script in a brick:
local giver = 1
function onClicked()
game.Players.[I NEED THE PLAYER NAME HERE].leaderstats.Clicks.Value = game.Players.[I NEED THE PLAYER NAME HERE].leaderstats.Clicks.Value + giver
end
script.Parent.ClickDetector.MouseClick:connect(onClicked)
Now I need to somehow get the player's name that clicked it and put it where I need to.
The ClickDetectors's MouseClick event have the "Clicking Player" as parameter, so you can do it like this:
local giver = 1
function onClicked(Player)
Player.leaderstats.Clicks.Value = Player.leaderstats.Clicks.Value + giver
end
script.Parent.ClickDetector.MouseClick:connect(onClicked)
However, this requires the FilteringEnabled to be set to false (not recomended).
To solve this, make a LocalScript in the brick with the code:
script.Parent.ClickDetector.MouseClick:connect(function(Player)
game.ReplicatedStorage:WaitForChild("BrickClick"):InvokeServer(script.Parent)
end)
And in a Script placed in the ServerScriptService put:
local Listener = game.ReplicatedStorage:FindFirstChild("BrickClick")
if Listener == nil then
Listener = Instance.new("RemoteFunction")
Listener.Name = "BrickClick"
Listener.Parent = game.ReplicatedStorage
end
function Listener.OnServerInvoke(Player,Brick)
Player.leaderstats.Clicks.Value = Player.leaderstats.Clicks.Value + 1
end
I won't point you to the wiki page for further reading, even thought it contains a bit of what you need, it contains too little information.
The ClickDetector's MouseClick info, the guide about FilteringEnabled and the guide about RemoteFunctions are better.
Try this!
script.Parent.MouseClick:Connect(function(Player)
-- Kill The Player
-- The parameter is referring to game.Players So if you want to do a kill button use .Character
Player.Character:BreakJoints()
-- Change The Color To Red (Other details)
script.Parent.Parent.BrickColor = BrickColor.new("Really red")
script.Parent.MaxActivationDistance = 0
-- Wait 4 Secs
wait(5)
-- Change The Color To Green
script.Parent.Parent.BrickColor = BrickColor.new("Lime green")
script.Parent.MaxActivationDistance = 50
end)