All examples of animated widgets I can find require a stateful widget and animate a change when setState is called to change the value of a field. Is there a way to combine a StreamBuilder with an animation?
I have tried putting an animated widget within the build method of the stream builder, but that does not result in any animation because it creates a new animated widget on each change and no transition is seen. I would have expected to find an optional 'stream' parameter on an animated widget to tell it to animate whenever a new value arrives on the stream. What can I add to this example to make it animate between value changes? (For example a simple linear transition).
import 'dart:math';
import 'package:flutter/material.dart';
import 'package:rxdart/rxdart.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
home: MyHomePage(),
);
}
}
class MyHomePage extends StatelessWidget {
@override
Widget build(BuildContext context) {
return Scaffold(
body: Center(
child: StreamBuilder(
stream: DataStreamSource().dataStream,
initialData: 50,
builder: (BuildContext buildContext, AsyncSnapshot<int> snapshot) {
return InkWell(onTap: DataStreamSource().generate, child: Container(height: snapshot.data?.toDouble(), width: snapshot.data?.toDouble(), color: Colors.deepOrange));
})));
}
}
class DataStreamSource {
static final DataStreamSource _instance = DataStreamSource._internal();
factory DataStreamSource() => _instance;
DataStreamSource._internal();
final BehaviorSubject<int> _dataController = BehaviorSubject();
Stream<int> get dataStream => _dataController.stream;
void generate() => _dataController.add(Random().nextInt(100) + 100);
}
In your provided example you can just change
ContainertoAnimatedContainerand it will "just work":Working Dartpad example here.
After the stream triggers a rebuild, Flutter matches the state for
AnimatedContainerto the new instance ofAnimatedContainer. That state then finds that the width and height values have changed and performs the animation. Flutter is able to match the state to each updated instance of the widget because the widget tree has the same structure each time. If you have a more complex use case involving widgets that can be replaced, have multiple siblings of the same type, etc., you might need to use keys to keep everything working properly. See this video for more details.