β‘ reactivity
A minimal and elegant state management solution for Flutter
Rebuild only what matters β with zero boilerplate.
β Built for performance
π§ Easy to learn
π― Flutter-native
π Perfect for UI-driven apps
𧨠The Power of ValueState
+ Named Records
The core feature of
reactivity
is seamless support for Dart Records viaValueState
.
With ValueState
, you manage multiple pieces of state β like name
, age
, isAdmin
β using a single named record, with full type safety and zero boilerplate.
π€― Example: Clean and Reactive
final user = ValueState<({String name, int age, bool isAdmin})>();
ReactiveState(user.on(
(u) => Text('Name: ${u.name}, Age: ${u.age}, Admin: ${u.isAdmin}'),
));
user.refreshWith((name: 'Felipe', age: 30, isAdmin: true));
β No classes
β Fully typed
β Instantly reactive
β Native Dart syntax
If you love Dartβs record syntax, this will feel like magic.
β¨ Features Overview
- π
refresh()
β global rebuild trigger - π§©
Reactive
,ReactiveState
,ReactiveStatus
,ReactiveShow
β declarative reactive widgets - π§±
ValueState
,InitedState
,VoidState
β flexible state containers - π¦
refreshStatus()
β reactive flow using enums - β
ReactiveNullable
,ReactiveNullableList
β handle nulls & empty states gracefully
π Getting Started
Add the dependency:
dependencies:
reactivity: ^1.0.0
Import it in your Dart file:
import 'package:reactivity/reactivity.dart';
β Usage Examples
Global rebuild
int counter = 0;
Reactive(() => Text('Counter: $counter'));
counter++;
refresh(); // Triggers rebuild
Rebuild by key
final myKey = ReactiveKey();
Reactive(() => Text("Hello"), reactiveKey: myKey);
refreshOnly(myKey); // Rebuild just this one
π§± State Containers
InitedState
final name = InitedState<String>("Kaian");
ReactiveState(name.on((value) => Text("Hello $value")));
name.refreshWith("Felipe");
ValueState
final count = ValueState<int>();
ReactiveState(count.on((value) => Text('Count: $value')));
count.refreshWith(1);
count.refreshUpdate((value) => value! + 1);
VoidState
final trigger = VoidState();
ReactiveState(trigger.on(() => Text("Triggered!")));
trigger.refresh();
π¦ ReactiveStatus
enum Status { loading, success, error }
refreshStatus(Status.loading);
ReactiveStatus<Status>(
cases: {
Status.loading: () => CircularProgressIndicator(),
Status.success: () => Text("Done!"),
Status.error: () => Text("Oops"),
},
defaultCase: () => Text("Idle"),
);
π Conditional Rendering
ReactiveShow
bool isLogged = false;
ReactiveShow(
showIf: () => isLogged,
builder: () => Text("Welcome"),
elseShow: Text("Login required"),
);
isLogged = true;
refresh();
ReactiveNullable
String? username;
ReactiveNullable<String>(
value: username,
builder: (name) => Text("Hi $name"),
ifNull: Text("No user"),
);
username = "Felipe";
refresh();
ReactiveNullableList
List<String>? items;
ReactiveNullableList<String>(
values: items,
builder: (list) => ListView(children: list.map(Text.new).toList()),
ifNull: CircularProgressIndicator(),
ifEmpty: Text("No items"),
);
β
Why reactivity
?
- π First-class support for Dart Named Records
- π« No
context
, noclasses
, no scope hassles - π§Ό Clean and minimal API
- π¬ Declarative, expressive, and beautiful
- π― Native to the Flutter widget tree
π€ Contributing
Got ideas or found bugs?
Feel free to open issues or submit a pull request. Let's build this together!
π License
MIT License Β© Felipe Kaian