import 'package:flutter/material.dart';
void main() => runApp(const MyApp());
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return const MaterialApp(
debugShowCheckedModeBanner: false,
home: AnimatedListExample(),
);
}
}
class AnimatedListExample extends StatefulWidget {
const AnimatedListExample({super.key});
@override
State<AnimatedListExample> createState() => _AnimatedListExampleState();
}
class _AnimatedListExampleState extends State<AnimatedListExample> {
final GlobalKey<AnimatedListState> _listKey = GlobalKey<AnimatedListState>();
final List<int> _items = List.generate(10, (index) => index);
void _removeItem(int index) {
final removedItem = _items[index];
_listKey.currentState?.removeItem(
index,
(context, animation) => SizeTransition(
sizeFactor: animation,
child: _buildItem(removedItem, animation, isRemoved: true),
),
// 👇 Long delay so you can press "Remove All" while it’s still animating
duration: const Duration(seconds: 10),
);
_items.removeAt(index);
}
void _removeAll() {
_listKey.currentState?.removeAllItems(
(context, animation) {
return SizeTransition(
sizeFactor: animation,
child: Container(
color: Colors.red[100],
child: const ListTile(
title: Text("Removing..."),
),
),
);
},
duration: const Duration(seconds: 2),
);
_items.clear();
}
Widget _buildItem(
int item,
Animation<double> animation, {
bool isRemoved = false,
}) {
return SizeTransition(
sizeFactor: animation,
child: Card(
margin: const EdgeInsets.symmetric(vertical: 4, horizontal: 8),
child: ListTile(
title: Text("Item $item"),
trailing: !isRemoved
? IconButton(
icon: const Icon(Icons.delete, color: Colors.red),
onPressed: () {
final index = _items.indexOf(item);
if (index != -1) _removeItem(index);
},
)
: null,
),
),
);
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text("AnimatedList Example"),
actions: [
TextButton(
onPressed: _items.isNotEmpty ? _removeAll : null,
child: Text("Clear list"),
),
],
),
body: AnimatedList.separated(
removedSeparatorBuilder: (context, index, animation) => SizedBox(),
separatorBuilder: (context, index, animation) => SizedBox(),
key: _listKey,
initialItemCount: _items.length,
itemBuilder: (context, index, animation) {
return _buildItem(_items[index], animation);
},
),
);
}
}
Steps to reproduce
The issue is continuation of #176362.
The issue is replicating on
AnimatedList.separatedversion of list.Expected results
last item should be deleted without exception
Actual results
An exception is thrown
The following assertion was thrown while handling a gesture:
'package:flutter/src/widgets/animated_scroll_view.dart': Failed assertion: line 1398 pos 12: 'itemIndex >= 0 && itemIndex < _itemsCount': is not true.
Code sample
Code sample
Screenshots or Video
Screenshots / Video demonstration
[Upload media here]
Logs
Logs
Flutter Doctor output
Doctor output