Reactivity
Signals, Computed values, and Effects. The core of Fluxy.
Reactivity
Fluxy's reactivity is built on three main primitives: Signals, Computed, and Effects.
Signals (flux)
flux creates a mutable signal. Signals are containers for values that can change over time.
final count = flux(0);
// Set value
count.value = 5;
// Read value (creates a dependency)
print(count.value);When you read a signal inside a reactive context (like an effect or a Fx widget builder), that context automatically subscribes to the signal.
Computed
computed creates a derived signal that depends on other signals.
final count = flux(0);
final doubleCount = computed(() => count.value * 2);doubleCount will automatically update whenever count updates. It is lazily evaluated and cached. It will only recompute when its value is accessed or when its dependencies change.
Effects
effect runs a function immediately and re-runs it whenever any of its dependencies change.
effect(() {
print("Count is now: ${count.value}");
});This is useful for side effects like logging, manual DOM updates, or triggering network requests.
Reactivity in UI
To make your UI reactive, you have two primary options:
The Fx Factory
Wrap any widget builder in Fx(() => ...) to automatically subscribe to any signals used inside. This triggers atomic rebuilds only for that specific widget.
final count = flux(0);
// Only this Text widget rebuilds when count changes
Fx(() => Text("Count: ${count.value}")) Reactive Text Shorthand
For simple text display, use Fx.text(() => signal.value).
Fx.text(() => "Current: ${count.value}");Two-Way Binding
Fluxy v0.1.4 provides native two-way binding for interactive components. Instead of manually handling onChanged and controller.text, you can bind a signal directly.
FxTextField
Binds its text content to a Signal<String>.
final username = flux("");
FxTextField(
label: "Username",
value: username, // Two-way binding
)FxDropdown
Binds its selection to a Signal<T>.
final theme = flux("Light");
FxDropdown<String>(
value: theme, // Two-way binding
options: ["Light", "Dark", "System"],
)Automatic Cleanup
Effects and subscriptions created within a widget's lifecycle are automatically disposed of when the widget is destroyed, preventing memory leaks.