Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Explain that images will not displayed when scrolling fast #8437

Closed
wongkoo opened this issue Sep 24, 2021 · 7 comments
Closed

Explain that images will not displayed when scrolling fast #8437

wongkoo opened this issue Sep 24, 2021 · 7 comments
Labels
a.cookbook Relates to a cookbook recipe or guide e2-days Effort: < 5 days fix.code-sample Needs new or updated code sample p3-low Valid but not urgent concern. Resolve when possible. Encourage upvote to surface. t.framework Relates to Flutter framework t.ui.assets Relates to adding or changing images, videos, and other assets t.ui.scrolling Relates to a scrolling UI widget

Comments

@wongkoo
Copy link

wongkoo commented Sep 24, 2021

Background

In scrolling containers, we often scroll quickly, and we find that pictures are often not displayed, resulting in a large area of blank space. We located this should be an optimization made by ScrollAwareImageProvider when the container is scrolling quickly to improve the smoothness of scrolling. But this loss of user experience, I hope this feature can be manually turned off.

By modifying the source code, we tested two cases respectively, which can be seen in the video below.

Steps to Reproduce

  1. Run flutter create bug.
  2. Update the files as follows:
    For some reasons, I can’t post the Image links, so you need to manually add it in the demo
import 'package:flutter/material.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
      home: MyHomePage(title: 'Flutter Demo Home Page'),
    );
  }
}

class MyHomePage extends StatefulWidget {
  MyHomePage({Key? key, required this.title}) : super(key: key);
  final String title;
  @override
  _MyHomePageState createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  List<String> urls = []; //needs to set image urls

  @override
  void initState() {
    super.initState();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text(widget.title),
      ),
      body: GridView.builder(
        gridDelegate:
            SliverGridDelegateWithFixedCrossAxisCount(crossAxisCount: 2),
        itemCount: urls.length,
        itemBuilder: (context, index) {
          return Container(
            height: 270,
            child: Image.network(urls[index]),
          );
        },
      ),
    );
  }
}

  1. fast scroll the gridView
  2. When the ImageCache is full, this phenomenon becomes more obvious

Expected results:
without using ScrollAwareImageProvider, The Image can be displayed normally

  void _resolveImage() {
    final ImageStream newStream =
    widget.image.resolve(createLocalImageConfiguration(
        context,
        size: widget.width != null && widget.height != null ? Size(widget.width!, widget.height!) : null,
      ));
    assert(newStream != null);
    _updateSourceStream(newStream);
  }
output.withoutScrollAware.mp4

Actual results:

  void _resolveImage() {
    final ScrollAwareImageProvider provider = ScrollAwareImageProvider<Object>(
      context: _scrollAwareContext,
      imageProvider: widget.image,
    );
    final ImageStream newStream =
    provider.resolve(createLocalImageConfiguration(
        context,
        size: widget.width != null && widget.height != null ? Size(widget.width!, widget.height!) : null,
      ));
    assert(newStream != null);
    _updateSourceStream(newStream);
  }
output.ScrollAware.mp4
Logs
[✓] Flutter (Channel flutter-2.6-candidate.9, 2.6.0-6.0.pre.65, on macOS 11.5.2 20G95 darwin-x64, locale zh-Hans-CN)
    • Flutter version 2.6.0-6.0.pre.65 at /Users/wangzhenhui/Documents/code/flutter_github
    • Upstream repository https://github.com/flutter/flutter.git
    • Framework revision b2550fe5fa (13 天前), 2021-09-11 11:17:04 +0800
    • Engine revision 45dc2fee13
    • Dart version 2.15.0 (build 2.15.0-96.0.dev)
    • Flutter download mirror http://flutter-storage.alibaba-inc.com/xianyu

[!] Android toolchain - develop for Android devices (Android SDK version 29.0.2)
    • Android SDK at /Users/wangzhenhui/Library/Android/sdk
    ✗ cmdline-tools component is missing
      Run `path/to/sdkmanager --install "cmdline-tools;latest"`
      See https://developer.android.com/studio/command-line for more details.
    ✗ Android license status unknown.
      Run `flutter doctor --android-licenses` to accept the SDK licenses.
      See https://flutter.dev/docs/get-started/install/macos#android-setup for more details.

[!] Xcode - develop for iOS and macOS (Xcode 13.0)
    • Xcode at /Applications/Xcode.app/Contents/Developer
    ! CocoaPods 1.7.5 out of date (1.10.0 is recommended).
        CocoaPods is used to retrieve the iOS and macOS platform side's plugin code that responds to your plugin usage on the Dart side.
        Without CocoaPods, plugins will not work on iOS or macOS.
        For more info, see https://flutter.dev/platform-plugins
      To upgrade see https://guides.cocoapods.org/using/getting-started.html#installation for instructions.

[✓] Chrome - develop for the web
    • Chrome at /Applications/Google Chrome.app/Contents/MacOS/Google Chrome

[✓] Android Studio (version 2020.3)
    • Android Studio at /Applications/Android Studio.app/Contents
    • Flutter plugin can be installed from:
      🔨 https://plugins.jetbrains.com/plugin/9212-flutter
    • Dart plugin can be installed from:
      🔨 https://plugins.jetbrains.com/plugin/6351-dart
    • Java version OpenJDK Runtime Environment (build 11.0.10+0-b96-7281165)

[✓] IntelliJ IDEA Community Edition (version 2020.1)
    • IntelliJ at /Applications/IntelliJ IDEA CE.app
    • Flutter plugin can be installed from:
      🔨 https://plugins.jetbrains.com/plugin/9212-flutter
    • Dart plugin can be installed from:
      🔨 https://plugins.jetbrains.com/plugin/6351-dart

[✓] VS Code (version 1.60.1)
    • VS Code at /Applications/Visual Studio Code.app/Contents
    • Flutter extension version 3.26.0

[✓] Connected device (3 available)


! Doctor found issues in 2 categories.

@dnfield
Copy link
Contributor

dnfield commented Sep 24, 2021

You can avoid this by providing custom scroll physics on the scrollable itself instead - see https://api.flutter.dev/flutter/widgets/ScrollPhysics/recommendDeferredLoading.html

Since you seem to want to load all images no matter how fast the scrolling is happening, that would be the better way to handle it - however, I'd caution you that on lower end devices you may run out of memory, particularly in iPhone devices that tend to have less memory and be more aggressive about OOM killing.

@wongkoo
Copy link
Author

wongkoo commented Sep 25, 2021

@dnfield Thank you for your reply.

The method you mentioned can indeed turn off this feature, but it will turn it off completely.

Normally, in a scrolling container, each unit will have multiple pictures. We only want the main picture to be displayed quickly, and other unimportant icons are displayed according to the scrolling speed.

In summary, we need to control certain pictures not to be affected by scroll speed, but not all.

item_example

@dnfield
Copy link
Contributor

dnfield commented Sep 25, 2021

If you precache the images that are important to show, they will display even if the scrolling speed is high. It's a good idea to do that because that way you will be more certain of actually rendering them even if the user is scrolling rapidly.

@dnfield
Copy link
Contributor

dnfield commented Sep 25, 2021

And in fairness, this is probably something that should be documented better...

@wongkoo
Copy link
Author

wongkoo commented Sep 26, 2021

I thought about it, if I use precacheImage, when there are hundreds of units, I can only write like this:

    GridView.builder(
      gridDelegate:
          SliverGridDelegateWithFixedCrossAxisCount(crossAxisCount: 2),
      itemCount: urls.length,
      itemBuilder: (context, index) {
        precacheImage(NetworkImage('index_main_image_url'), context);

        return Container(
          height: 270,
          child: Image.network('index_main_image_url'),
        );
      },
    );

This seems feasible, but it is a bit complicated. For those who have not looked at the source code, it may not be clear that there will be fast scrolling optimization, and it seems difficult to think of what to do. This can indeed be solved by improving the documentation.

I think scrollAwareEnable in PR can reduce the cost of this optimization.

By the way, does the precacheImage interface need to be optimized? My immature idea, I commented in the issue before: flutter/flutter#27227 (comment)

@TahaTesser TahaTesser added st.triage.triage-team Triage team reviewing and categorizing the issue and removed st.triage.triage-team Triage team reviewing and categorizing the issue labels Sep 28, 2021
@TahaTesser
Copy link
Member

Labelling this documentation, perhaps a cookbook on Flutter website too?

@TahaTesser TahaTesser added d: cookbook t.ui.scrolling Relates to a scrolling UI widget t.framework Relates to Flutter framework labels Sep 28, 2021
@goderbauer goderbauer added the P4 label Mar 23, 2022
@Hixie Hixie transferred this issue from flutter/flutter Mar 24, 2023
@atsansone atsansone added fix.code-sample Needs new or updated code sample t.ui.assets Relates to adding or changing images, videos, and other assets a.cookbook Relates to a cookbook recipe or guide p3-low Valid but not urgent concern. Resolve when possible. Encourage upvote to surface. e2-days Effort: < 5 days and removed d: examples labels May 30, 2023
@atsansone atsansone changed the title The Image will not displayed when scrolling fast Explain that images will not displayed when scrolling fast Jun 3, 2023
@atsansone
Copy link
Contributor

This looks to be a feature, not a bug. This appears to have been documented in this breaking change in #3622. Closing this issue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
a.cookbook Relates to a cookbook recipe or guide e2-days Effort: < 5 days fix.code-sample Needs new or updated code sample p3-low Valid but not urgent concern. Resolve when possible. Encourage upvote to surface. t.framework Relates to Flutter framework t.ui.assets Relates to adding or changing images, videos, and other assets t.ui.scrolling Relates to a scrolling UI widget
Projects
None yet
5 participants