Difference between listening of stream by StreamBuilder and regular listen method

Viewed 2021

I'm using http library in order to download an image.

final client = http.Client();
final _response = await client.send(http.Request('GET', Uri.parse("my_url")));

Listening way 1: (listen method)

int downloaded = 0;
_response.stream.listen((value) {
  // this gets called 82 times and I receive actual image size
  downloaded += value.length;
});

Listening way 2: (StreamBuilder widget)

int downloaded = 0;
StreamBuilder<List<int>>(
  stream: _response.stream,
  builder: (_, snapshot) {
    // this gets called 11 times and I receive around 1/10 actual image size
    if (snapshot.hasData) downloaded += snapshot.data.length;
    return Container();
  },
);

The question is why StreamBuilder's build() method isn't getting called that often when new data arrives, it simply defeats the purpose of being used as a widget.

1 Answers

StreamBuilder is basically better optimized to not rebuilt on every new snapshot. As StreamBuilder documentation states:

Widget rebuilding is scheduled by each interaction, using State.setState, but is otherwise decoupled from the timing of the stream. The builder is called at the discretion of the Flutter pipeline, and will thus receive a timing-dependent sub-sequence of the snapshots that represent the interaction with the stream.

As an example, when interacting with a stream producing the integers 0 through 9, the builder may be called with any ordered sub-sequence of the following snapshots that includes the last one (the one with ConnectionState.done):

  • new AsyncSnapshot<int>.withData(ConnectionState.waiting, null)
  • new AsyncSnapshot<int>.withData(ConnectionState.active, 0)
  • new AsyncSnapshot<int>.withData(ConnectionState.active, 1)
  • ...
  • new AsyncSnapshot<int>.withData(ConnectionState.active, 9)
  • new AsyncSnapshot<int>.withData(ConnectionState.done, 9)

The actual sequence of invocations of the builder depends on the relative timing of events produced by the stream and the build rate of the Flutter pipeline.

Related