【问题标题】:Provider ValueNotifier listen not working on some Pages on FlutterProvider ValueNotifier 监听在 Flutter 上的某些页面上不起作用
【发布时间】:2020-08-29 15:28:29
【问题描述】:

listen 不工作。当热重载值更新时。

A页

  @override
  Widget build(BuildContext context) {

    ValueNotifier<List<ProductModel>> selectNotifier = Provider.of<ValueNotifier<List<ProductModel>>>(context, listen: true);

小部件

 Text('${selectNotifier.value.length}'),

页面 B

 InkWell(
     onTap: () {
         selectNotifier.value.add(selectProduct);                        
     },

ma​​in.dart

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MultiProvider(
      providers: [
        ChangeNotifierProvider<ValueNotifier<List<ProductModel>>>(
          create: (_) => ValueNotifier<List<ProductModel>>([]),
        ),
      ],
      child: MaterialApp(
        theme: CustomTheme.themeData,
        onGenerateRoute: Router.generateRoute,
        debugShowCheckedModeBanner: false,
      ),
    );
  }

版本

provider: ^4.1.2

Flutter 版本

1.17.2

我尝试了以下方法来解决此问题。但我不知道什么是正确的方式(最好的方式)。

第一种方式

降级 Flutter 和 Provider 后,现在可以正常工作了。这是为什么呢?

provider: 3.2.0
git checkout v1.12.13-hotfixes

第二种方式

或者它也以这种方式工作。//但在 IDE 上出现警告

onTap: () {
             selectNotifier.value.add(selectProduct); 
             selectNotifier.notifyListeners(); //info: The member 'notifyListeners' can only be used within instance members of subclasses of 'package:flutter/src/foundation/change_notifier.dart'.                      
         },

但是添加这个ChangeNotifier后警告消失了,

class _viewState extends State<View> with ChangeNotifier{

添加ChangeNotifier后也会出错

在最终确定小部件树时引发了以下断言: _CartItemViewState.dispose 调用 super.dispose 失败。

dispose() 实现必须始终调用它们的超类 dispose() 方法,以确保小部件使用的所有资源都完全 发布。

第三种方式

我在这种方式上没有遇到任何问题,但是我在生产应用程序中使用了这么多 ValueNotifier,所以,其他的不是列表。我不知道如何更改其他类型。

 onTap: () {
        selectNotifier.value = List.from(selectNotifier.value)..add(widget.productModel);
}

【问题讨论】:

    标签: flutter dart flutter-provider


    【解决方案1】:

    在这个问题中,第三种方式是正确的方式。

    onTap: () {
            selectNotifier.value = List.from(selectNotifier.value)..add(widget.productModel);
    }
    

    【讨论】:

    • 这很漂亮。
    • 但是,这很困难:使用List.from 复制列表是有代价的。或者使用ValueNotifier 子类,以及用于改变列表的方法,并在所述方法中使用notifyListeners(),在某些情况下会提高性能(列表太大和/或列表更新太频繁)
    • 在这里查看整个讨论github.com/flutter/flutter/issues/29958
    猜你喜欢
    • 2020-12-30
    • 1970-01-01
    • 2012-04-13
    • 2019-06-14
    • 2015-06-04
    • 1970-01-01
    • 2018-06-14
    • 2016-12-04
    • 1970-01-01
    相关资源
    最近更新 更多