Bindings
ui.bind(instance, bindings) attaches behavior to UI that already exists. Named
keys resolve to a property, event, or direct child. Array entries compose binding
fragments.
local stop = ui.bind(button, {
baseStyle,
hoverSounds(),
Text = function(): string
return if busy() then "Please wait" else label()
end,
Activated = submit,
UIScale = {
Scale = animatedScale,
},
})
Property functions are tracked expressions. Event functions are callbacks. Child tables recurse into an existing child with the exact key name.
ui.Binding<T> is exported for annotations. Its generic parameter records the
root Instance type, while its entries stay open because Roblox properties,
events, named children, and numeric fragments share the same table. bind
checks those entries when it mounts them. This avoids recursive compile-time
type evaluation on large Instance types.
local bindings: ui.Binding<TextButton> = {
Text = "Save",
Activated = function(inputObject: InputObject, clickCount: number)
print(inputObject, clickCount)
end,
UIScale = {
Scale = 1,
},
}
ui.bind(existingButton, bindings)
Reactive structure
An array function can return a binding fragment or nil. Its dependencies decide
when the branch is replaced.
ui.bind(button, {
{ BackgroundTransparency = 0 },
function()
return if selected() then {
BackgroundTransparency = 0.2,
UIStroke = { Enabled = true },
} else nil
end,
})
Later active fragments take priority. Removing a fragment reveals the previous writer. Stopping the root bind restores the property value captured before the first writer and disconnects every event and reactive branch.
The bind owns only work it creates: property subscriptions, tracked binding
functions, event connections declared in the binding table, and reactive
branches. It does not destroy the root or child Instances. It also cannot clean
up connections or Instances that application code creates outside a tracked
binding function. Register such work with ui.cleanup inside that function, or
manage it manually.
Fragments are ordinary tables, so components are ordinary functions that return tables. No component constructor or merge helper is needed.