0 purchases
stacker2
stacker #
A collection of 3 widgets that stack their children, displaying a
single child at a time, transitioning between children when a different
child is displayed.
Stacker can be used modularly as a component, to drive single-page apps,
or to control multi-step flows within a widget or page.
Usage #
import 'package:stacker2/stacker.dart';
copied to clipboard
StackSwapper #
[StackSwapper] is the simplest of the three widgets. It accepts a single
child and implicity transitions to displaying a new child when its child
is updated.
/// The child being displayed by the [StackSwapper].
var child = Container(child: Text('A'));
/// Transitions [StackSwapper] to displaying a different widget.
void updateChild() {
child = Container(child: Text('B'));
setState(() {});
}
/// Build the [StackSwapper].
@override
Widget build(BuildContext context) {
return StackSwapper(child);
}
copied to clipboard
StackSwitcher #
[StackSwitcher] accepts a list of children and the index of the child
that should be displayed. When the index is changed it will transition
to displaying the child at the new index.
/// The children contained in [StackSwitcher]'s stack.
final children = <Widget>[
Container(child: Text('A')),
Container(child: Text('B')),
Container(child: Text('C')),
Container(child: Text('D')),
Container(child: Text('E')),
];
/// The index of the child in [children] currently being
/// dispalyed by the [StackSwitcher].
var currentChild = 0;
/// Transitions [StackSwitcher] to displaying the next child in the list.
void nextChild() {
currentChild = (currentChild + 1) % children.length;
setState(() {});
}
/// Build the [StackSwitcher].
@override
Widget build(BuildContext context) {
return StackSwitcher(children, child: currentChild);
}
copied to clipboard
Maintaining States #
The states of every child in the stack can be maintained when they're
not visible by setting the [maintainStates], [maintainAnimations], or
[maintainSizes] parameters to true.
[maintainStates] will maintain the state of the child.
[maintainAnimations] will keep the animation ticker providers active
while the children are hidden. Setting this to true will automatically
set [maintainStates] to true.
[maintainSizes] will maintain the space the hidden children would occupy
if they were visible. Setting this to true will automatically set
[maintainAnimations] and [maintainStates] to true.
/// A [StackSwitcher] where every child's state will
/// be maintained when they're hidden.
StackSwitcher(
children,
child: currentChild,
maintainStates: true,
);
copied to clipboard
An individual child's state/animation/size can be maintained by wrapping the
child in a [MaintainState] widget.
[MaintainState] has 2 parameters, [maintainAnimation] and [maintainSize].
Setting [maintainSize] to true will automatically set [maintainAnimation]
to true.
/// A list of children whose states will be maintained, or not,
/// independently of one another.
final children = <Widget>[
// The state of this widget will be maintained when it is hidden.
MaintainState(MyStatefulWidget())),
// The state of this child will not be maintained when it is hidden.
MyStatefulWidget(),
// The state and animation tickers of this widget will be
// maintained when it is hidden.
MaintainState(
MyStatefulWidget(),
maintainAnimation: true,
),
// The state of this child will not be maintained when it is hidden.
MyStatefulWidget(),
// The state, animation tickers, and size of this widget will be
// maintained when it is hidden.
MaintainState(
MyStatefulWidget(),
maintainSize: true,
),
];
copied to clipboard
Stacker #
[Stacker] accepts a single child, which acts as the root of a linear
history of widgets, which can be navigated (like a browser's back and
forward buttons.)
New children can be built, inserted into, or removed from the stack on
the fly.
There a number of direct methods for controlling and navigating
the stack, which are accessed from the [Stacker]'s instance.
All of [Stacker]'s navigation/build methods have an optional [onComplete]
parameter, which can be used to provide a callback that will be called a
single time when the transition triggered by that method completes.
/// An instance of a [Stacker]. By storing the [Stacker] as an instance,
/// its direct methods can be used to control it.
final myStacker = Stacker(MyRootWidget());
/// Builds and transitions to a new [child].
void build(Widget child, {VoidCallback onComplete}) {
myStacker.build(child, onComplete: onComplete);
}
/// Transitions to the child before the child currently being displayed.
void back({VoidCallback onComplete}) {
myStacker.back(onComplete: onComplete);
}
/// Transitions to the child after the child currently being displayed.
void forward({VoidCallback onComplete}) {
myStacker.forward(onComplete: onComplete);
}
/// Transitions to the child at [index].
void open(int index, {VoidCallback onComplete}) {
myStacker.open(index, onComplete: onComplete);
}
/// Transitions to the child before the child currently being displayed,
/// and removing the current child and every child after it from the history.
void pop({VoidCallback onComplete}) {
myStacker.pop(onComplete: onComplete);
}
/// Transitions to the root child.
void root({VoidCallback onComplete}) {
myStacker.root(onComplete: onComplete);
}
copied to clipboard
Those same methods are also accessible from any of the [Stacker]'s
children via a [BuildContext] extension by calling [context] within
a [StatelessWidget]'s [build] method, or anywhere within a [State].
Note: These have the same optional parameters as their respective
equivalent methods listed above and in the section below.
// Builds and transitions to a new child.
context.stacker.build(child);
// Transitions to the previous child.
context.stacker.back();
// Transitions to the next child.
context.stacker.forward();
// Transitions to the child at [index].
context.stacker.open(index);
// Transitions the previous child and clears the history.
context.stacker.pop();
// Transitions to the root child.
context.stacker.root();
copied to clipboard
Note: If a [Stacker] is built directly by its parent's [build] method,
only its children will be able to access the methods to control the stacker,
which may be all you need depending on the use-case.
/// The [Stacker] built here can only be controlled by
/// [MyRootWidget] or any other children added to it.
@override
Widget build(BuildContext context) {
return Stacker(MyRootWidget());
}
copied to clipboard
Managing the History #
The history can be cleared by calling [clearHistory]. The history is also
cleared when building or appending a widget to the history, unless the [build]
or [append] methods' [clearHistory] parameter is changed to false, or when
navigating to the root child by setting the [clearHistory] parameter to true.
/// Builds and transitions to a new [child], clearing the history
/// by default.
///
/// If [clearHistory] is set to `false`, every child in the forward
/// history will be pushed back when the new [child] is built.
void build(Widget child, {bool clearHistory = true}) {
myStacker.build(child, clearHistory: clearHistory);
}
/// Transitions to the root widget in the stack, clearing the history
/// if [clearHistory] is set to `true`.
void root({bool clearHistory = false}) {
myStacker.root(clearHistory: clearHistory);
}
copied to clipboard
Children can be inserted into or removed from the history by any of
the below methods.
/// Inserts a [child] into the stack before the one currently
/// being displayed.
void prepend(Widget child) {
myStacker.prepend(child);
}
/// Inserts a [child] into the stack after the one currently
/// being displayed, clearing the history by default.
void append(Widget child, {bool clearHistory = true}) {
myStacker.append(child, clearHistory: clearHistory);
}
/// Inserts a [child] into the stack at [index], pushing
/// every child occuring on or after [index] back.
void insert(int index, Widget child) {
myStacker.insert(index, child);
}
/// Removes the first instance of [child] from the stack.
void remove(Widget child) {
myStacker.remove(child);
}
/// Removes the child from the stack at [index].
void removeAt(int index) {
myStacker.removeAt(index);
}
/// Removes every widget from stack after the one currently
/// being diplayed, clearing the forward history.
///
/// If [skip] is `> 0`, that number of widgets after the one currently
/// being displayed will be retained in the history.
void clearHistory([int skip = 0]) {
myStacker.clearHistory(skip);
}
copied to clipboard
All of the above methods are also accessible to a [Stacker]'s children
via the [BuildContext] extension. Note: These methods have the same
optional parameters as their respective equivalents listed above.
// Inserts a child into the stack before the one currently
// being displayed.
context.stacker.prepend(child);
// Inserts a child into the stack after the one currently
// being displayed, clearing the history by default.
context.stacker.append(child);
// Inserts a [child] into the stack at [index], pushing
// every child occuring on or after [index] back.
context.stacker.insert(index, child);
// Removes the first instance of [child] from the stack.
context.stacker.remove(child);
// Removes the child from the stack at [index].
context.stacker.removeAt(index);
// Removes every widget from stack after the one currently
// being diplayed
context.stacker.clearHistory();
copied to clipboard
Android Back Button #
The [backButton] parameter can be set to true to have the [Stacker]
intercept the Android back button and navigate backwards in the [Stacker]'s
history when it's pressed.
/// This [Stacker] can be navigated with Android's back button.
Stacker(
MyRootWidget(),
backButton: true,
);
copied to clipboard
If the root child is being displayed, the back button will defer to the
default behavior.
Maintaining States #
A [Stacker]'s childrens' states can be maintained in the same way as a
[StackSwitcher]s', either by setting the [maintainStates], [maintainAnimations],
or [maintainSizes] parameters to true, or by wrapping individual children
in a [MaintainState] widget.
Parameters #
Each of the widgets have a number of shared parameters used to provide
callbacks or to customize their transition animation.
Transitions #
The transitions between children are handled by a
FadeAndTranslate widget,
which fades each child in/out while translating their positional offsets.
There are several parameters used to specify the duration, offset, and
additional behavior of the transitions.
/// A [StackSwapper] built with the default parameters..
StackSwapper(
myWidget,
// The duration of the transition animation.
transitionDuration: Duration(milliseconds: 240),
// The offset the children translate to during the transition.
transitionTranslation: Offset(0.0, -24.0),
// If `true`, the children will translate in opposite directions,
// if `false`, they'll translate in the same direction.
invertTranslations: true,
// If `true`, the first child built will transition from being hidden
// to being visible, if `false`, it will be built as visible.
transitionFirstChild: false,
),
copied to clipboard
Note: [StackSwitcher] and [Stacker] have the same default values
for their equivalent parameters as the [STackSwapper] above.
Callbacks #
Each of the widgets also accepts two callbacks, [onSwitchStart] and
[onSwitchComplete], which are called each time a transition starts
and completes, respectively.
Stacker(
myWidget,
// A callback called every time a transition starts.
onSwitchStart: () => print('Transition starting.'),
// A callback called every time a transition has completed.
onSwitchComplete: () => print('Transition completed.'),
);
copied to clipboard
For personal and professional use. You cannot resell or redistribute these repositories in their original state.
There are no reviews.