type s.none
Used as a replacement for nil
Example:
s:set({ undefined = s.none })
print(s.none) --> "none"
type s.all
A subscription key to watch all changes
Example:
s:subscribe(s.all, function)
print(s.all) --> "all"
map s.state
A map of the state store to read states
Example:
s:set({ counter = 0 })
print(s.state.counter) --> 0
function s.new(key)
Set state of keys and values and apply attributes if the store key is an instance and the value is a valid attribute type
Parameters:
key: any
-- the unique key for the store
Returns:
store
-- a state store
Example:
local playerStore = s.new(game.Players.LocalPlayer)
local gameStore = s.new(game)
method s:set(state, value?)
Set state of keys and values and apply attributes if the store key is an instance and the value is a valid attribute type
Parameters:
state: table | string
-- the state to setvalue: any?
-- an optional state to set as
Returns:
table
-- the updated state table
Example:
s:set({ counter = 0 })
s:set("counter", s.state.counter + 1)
s:set({
counter = s.state.counter + 1
})
method s:fire(state, value)
Fire all callbacks on the key provided with the updated value
Parameters:
state: string
-- the state to firevalue: any
-- the value to update with
Returns:
self
-- the store itself
Example:
s:fire("counter", 10)
method s:roact(component, keys?)
Initialize a roact component with the state store and injects the states from the store into the component
Parameters:
component: table
-- the roact component classkeys: table?
-- the optional keys (or all!) to inject state, leave nil for all
Returns:
component
-- return the roact component
Example:
return s:roact(Component, { "counter" }) -- track and inject counter into the component
return s:roact(Component) -- track and inject all state changes into the component
method s:define(interface)
Define an interface with t to filter state and maintain global changes to the store
Parameters:
interface: function
-- the t.interface or t.strictInterface function
Returns:
interface
-- returns the same t interface function
Example:
local interface = s:define(t.strictInterface({
counter = t.number,
flag = t.boolean,
}))
s:set({
counter = 0, -- ✅
flag = Color3.fromRGB(0, 0, 0), -- ❌
}) -- this will error since flag goes against the interface
method s:sanitize(value)
Sanitizes a data value to check if it's valid for an attribute and returns a boolean whether or not it is
Parameters:
value: table | any
-- the value or table of values to be sanitized
Returns:
boolean
-- true if passed, false if not
Example:
print("is number valid:", s:sanitize(0)) --> "is number valid: true"
print("is color3 valid:", s:sanitize(Color3.fromRGB(0, 0, 0,))) --> "is color3 valid: true"
print("is enum valid:", s:sanitize(Enum.Keycode.Q)) --> "is enum valid: false"
method s:subscribe(keys, callback)
Watch for changes on all keys or specified keys with a callback function. Use s.all
to tell the subscription to watch for all changes that occur.
Parameters:
keys: table | any
-- the keys to watch, uses.all
as your key to watch all changescallback: function
-- the function to call when a change occurs, provides acontext
object
Arguments:
context = { state: any, value: any }
-- the context object passed in the callback function with.state
and.value
Returns:
Subscription
-- returns a subscription object to disconnect the subscription
Example:
local subscription = s:subscribe(s.all, function(context)
print(context.state .. ",", context.value) --> "hello, world!"
end)
s:set({ hello = "world!" })
subscription:unsubscribe()
s:subscribe({ "counter", "stage" }, function(context)
if context.state == "counter" then
print("countdown:", context.value)
elseif context.state == "stage" then
print("moving to new stage:", context.value)
end
end)
method Subscription:unsubscribe()
Unsubscribes a subscription and disconnects the object
Returns:
nil
Example:
local subscription; subscription = s:subscribe(s.all, function(context)
subscription:unsubscribe()
end)
s:set({ counter = 0 })
This project is licensed under the MIT license. See LICENSE for details.