Hello, I tried to look everywhere and other topics but I can’t understand when to use bindables if I can just jam it into one script.
Bindable events and functions are for communicating between scripts of the same type, unlike Remote Events and functions that communicate between client and server scripts. A bindable even connected to a function can run on a “seperate” thread wheras a bindable function connected to a function has the ability to yield the script that fired the value and return a value. I recommend checking out these resources.
At some point you might run into a problem where you’d want script A to communicate with script B, or even with multiple scripts, for example have a vehicle script let the gui scripts know that the player has exited a vehicle or such.
In such scenarios, you can create a BindableEvent
and have one or more scripts running on the same peer connect to its event. You can also use a BindableFunction
if you need to ex. wait for a task to finish running and/or get a return value.
If you want a live example: roblox chat scripts use events for stuff such as a player joining the chat, so that the bunch of modules can all just listen to a single event.
Let’s go over the client-server model that Roblox has put in place.
The client has nearly no control over the server, aka what other players can see. The client is you, the player’s machine. The client can read inputs such as key presses, mouse clicks, and more. The server cannot read these inputs as it can’t know what the client is doing without it explicitly telling the server. That’s where remote events and functions come in!
Remote events allow you to communicate between the server and the client. Let’s say that you want to spawn a part in front of the player every time they click a gui button. The server won’t know if they’ve clicked the button because that is reliant on client input, and is not replicated for you. You can replicate it yourself by creating a remote event that fires from the client to the server whenever your player clicks that button. Below is an example script.
-- Server (normal script, also known as a server script)
local Event = game:GetService("ReplicatedStorage"):WaitForChild("EventName")
-- we usually put remote events in replicated storage, because
-- both the client AND the server can read from it, unlike
-- server storage.
local function SpawnPart(player)
local character = player.Character
local part = Instance.new("Part")
part.Parent = workspace
part.CFrame = character.PrimaryPart.CFrame * (character.PrimaryPart.CFrame.LookVector * 2)
-- If you don't understand what setting the part's "CFrame" does, that's okay!
-- This just sets the part's position in front of where the character is
-- looking.
end
Event.OnServerEvent:Connect(SpawnPart)
-- Client (local script)
local button = script.Parent -- this assumes the script is inside the gui button!
local event = game:GetService("ReplicatedStorage"):WaitForChild("EventName")
button.Activated:Connect(function()
event:FireServer()
end)
Do you see the usefulness now? Any time you want to communicate between the client and the server, remote events and remote functions have your back. You can create shop guis, magic systems, and more with the help of remote events and functions. If you’d like to learn more, please check out this page: Bindable Events and Functions | Roblox Creator Documentation
Yes, but they wanted to know about Bindable events and functions. Not Remote events and functions.
BindableEvents
What is that?
When it’s fired using BindableEvent:Fire()
function calls the function that is connected with BindableEvent.Event
event. Remember that it allows one-way communication (Server to Server, Client to Client). If you need two-way communication (Server to Client, Client to Server) use RemoteEvent
s instead.
When and how to use it?
You can use it, for example, when someone collects a coin, the game finishes, someone dies.
To use it, just create one, and start using it with Script
s or LocalScript
s. This is an example:
local bindableEvent = -- Put here your BindableEvent!
bindableEvent.Event:Connect(function(msg) -- Recieves the BindableEvent's signal
print(msg) --> Hello
end)
bindableEvent:Fire("Hello") -- Fires the BindableEvent
Valid values:
There are some values that you cannot send through BindableEvents
:
local bindableEvent = -- Put here your BindableEvent!
bindableEvent:Fire{1, nil, 2} --> Tables as arrays that have nil gaps
bindableEvent:Fire{
[{}] = "hello"; --> Table keys which are not numbers or strings
}
bindableEvent:Fire{ --> Table keys which are both numbers and strings
[1] = "apple",
hello = "world",
}
More Info: BindableEvent | Roblox Creator Documentation, Events | Roblox Creator Documentation
BindableFunctions
What is that?
When it’s invoked using BindableFunction:Invoke()
function calls BindableFunction.OnInvoke
callback and it can return values. Remember that it allows one-way communication (Server to Server, Client to Client). If you need two-way communication (Server to Client, Client to Server) use RemoteFunction
s instead.
When and how to use it?
You can use it, for example, to get a player’s points, request some object’s info.
To use it, just create one, and start using it with Script
s or LocalScript
s. This is an example:
local bindableFunction = -- Put here your BindableFunction!
bindableFunction.OnInvoke = function(number) -- Calls when the BindableFunction is invoked
local calculateDouble = number * 2
return calculateDouble
end
local double = bindableFunction:Invoke(5)
print(double) --> 10
CAUTION: BindableFunction:Invoke()
yields until the corresponding callback is found. If it was not set, it will not resume execution.
Valid values:
There are some values that you cannot send through BindableEventsFunction
s:
local bindableFunction = -- Put here your BindableFunction!
bindableFunction:Invoke{1, nil, 2} --> Tables as arrays that have nil gaps
bindableFunction:Invoke{
[{}] = "hello"; --> Table keys which are not numbers or strings
}
bindableFunction:Invoke{ --> Table keys which are both numbers and strings
[1] = "apple",
hello = "world",
}
More Info: BindableFunction | Roblox Creator Documentation, Functions | Roblox Creator Documentation
Hope it helps!
I already understand that. Thanks anyway.
Thanks but, I can write them in one script. What’s the point of bindables?
So, since you already know (I think) how remote events and functions work and when to use them, then the point of bindables is to be able to communicate between two separate scripts of the same type. So with a bindable event you can communicate and fire a function between two different local scripts. Or, alternatively, you could do the same with two server scripts. However, if you want to communicate between two different clients, then you would have to fire a remote event or function on the server (basically using the server as a proxy) so the server in turn could send the information to the other client.
For example, say I have two server scripts. I want to execute a function in script 2 that prints "Hello World"
in the output whenever script 1 detects a player added. So using a bindable event I would end up doing something like this:
Server Script 1:
-- Our Services
local Players = game:GetService("Players")
local ServerStorage = game:GetService("ServerStorage")
-- Our Objects AKA the bindable event
local BindableEvent = ServerStorage:FindFirstChild("ExampleEvent") or Instance.new("BindableEvent") -- This will create the event if it doesn't exist or retrieve the event if it does exist
BindableEvent.Name = "ExampleEvent"
BindableEvent.Parent = ServerStorage
Players.PlayerAdded:Connect(function(player)
BindableEvent:Fire() -- You can also pass any information you want into the parameters. So if you wanted to share the player name you could do BindableEvent:Fire(player.Name)
end)
Server Script 2
-- Our Services
local ServerStorage = game:GetService("ServerStorage")
-- Our Objects AKA the bindable event
local BindableEvent = ServerStorage:WaitForChild("ExampleEvent") -- This will retrieve the bindable event
-- When the event is fired
BindableEvent.Event:Connect(function() -- You can add any parameters here you want to be passed. So if you wanted the player name you could do function(name) with name as the player name passed
print("Hello World")
end)
This example will print hello world in another script whenever a player joins the game. It will execute any function connected to the BindableEvent | Roblox Creator Documentation in any server script.
Differences:
Quoted directly from the BindableFunction | Roblox Creator Documentation page:
BindableEvents vs BindableFunctions
Unlike BindableFunctions, BindableEvents
only allow for one-way communication between two scripts:
- When a script invokes a BindableFunction it yields until the event is handled and returned by the subscribed script synchronously. This allows for scripts to effectively pass data during and after an event.
- When a script fires a BindableEvent, however, it does not yield for a return. The script continues
executing as the event is handled by the subscribed script asynchronously.
Basically the `BindableFunction allows you to return a value, meaning that in the example I gave if you replaced script 1 and script 2 with a BindableFunction instead of an event it’d look like this:
Server Script One
-- Our Services
local Players = game:GetService("Players")
local ServerStorage = game:GetService("ServerStorage")
-- Our Objects AKA the bindable function
local BindableFunction = ServerStorage:FindFirstChild("ExampleFunction") or Instance.new("BindableFunction") -- This will create the function if it doesn't exist or retrieve the function if it does exist
BindableFunction.Name = "ExampleFunction"
BindableFunction.Parent = ServerStorage
Players.PlayerAdded:Connect(function(player)
local text = BindableFunction.Invoke() -- Like with the BindableEvent you can pass values through this call
print(text) -- This will print the text returned
end)
Server Script Two
-- Our Services
local ServerStorage = game:GetService("ServerStorage")
-- Our Objects AKA the bindable event
local BindableFunction = ServerStorage:WaitForChild("ExampleFunction") -- This will retrieve the bindable function
-- When the function is invoked
BindableFunction.OnInvoke = function() -- You can add any parameters here you want to be passed.
wait(5) -- This is an example to show this function is able to yield for any script that invokes the function
return "Hello World" -- you can return as many values as you want but they must be separated by a comma
end)
In this example, script one will print the text returned from script two.
Conclusion
In the end thats it! The difference between the two can be summed up as followed:
-
BindableEvent
’s are used for one-way communication between scripts. -
BindableFunction
’s are used for two-way communication between scripts.
In the end, whether or not you use bindable events or functions is up to you and the way you structure your code. They can be useful if you use multiple scripts in the game. However, if you want to have a function that all scripts can use then you should use a ModuleScript | Roblox Creator Documentation.
You can also check out the answer to another question similar to this: