🧠 Description
I have a ListView.builder (used for a chat screen) with the following properties:
ListView.builder(
reverse: true,
controller: _scrollController,
itemCount: messages.length,
itemBuilder: (context, index) {
// each message has a dynamic height
},
)
Each item (message) has dynamic height, and the list is reversed (reverse: true) so the latest messages appear at the bottom.
I need to scroll or jump to a specific index (or message ID) programmatically — for example, to scroll to message #30 when tapping a “Jump to” button.
What I’ve tried
Using:
_scrollController.jumpTo(offset);But this requires knowing the pixel offset, which is not possible with dynamic item heights.
Tried storing widget positions using:
RenderAbstractViewport.of(box)?.getOffsetToReveal(box, 0.0);This works only for built items (already visible in the viewport).
Items that are off-screen are not yet built, so theirRenderBoxis null.Tried using:
Scrollable.ensureVisible(context);But this also works only if the item is already built and has a valid
BuildContext.I cannot use external packages such as:
scrollable_positioned_listscroll_to_index
because of project constraints.
⚠️ Problem
ListView.builder lazily builds only visible items, so it’s impossible to know:
The pixel offset of unbuilt items (due to dynamic heights).
How to reliably scroll to a target index or message ID without pre-measuring all heights.
There is no native Flutter API to:
Query a child’s pixel offset by index before it’s built.
Request
ListViewto “jump to index X” natively.
Expected Behavior
A built-in way to:
listViewController.jumpToIndex(int index, {Alignment alignment = Alignment.center});
that:
Works with
reverse: trueSupports dynamic heights
Handles unbuilt (off-screen) items gracefully