【问题标题】:StatefulWidgets in ReorderableListView don't keep their state when reordering the listReorderableListView 中的 StatefulWidgets 在重新排序列表时不保持其状态
【发布时间】:2020-06-06 03:37:37
【问题描述】:

在这里,我有一个精简的页面,它创建了一个ReorderableListView,它的主体设置为两个RecipeStepWidgets 并设置了UniqueKeys(我也尝试过使用ValueKeyObjectKey

import 'package:flutter/material.dart';
import 'consts.dart';
import 'recipeStep.dart';
import 'recipeStepWidget.dart';

class NewRecipePage extends StatefulWidget {
  @override
  _NewRecipePageState createState() => _NewRecipePageState();
}

class _NewRecipePageState extends State<NewRecipePage> {
  final TextEditingController _nameController = TextEditingController();
  @override
  Widget build(BuildContext context) {
    List<RecipeStep> recipeSteps = [];

    List<RecipeStepWidget> stepWidgets = [
      RecipeStepWidget(key: UniqueKey()),
      RecipeStepWidget(key: UniqueKey())
    ];

    void _onReorder(int oldIndex, int newIndex) {
      setState(
        () {
          if (newIndex > oldIndex) {
            newIndex -= 1;
          }

          final RecipeStepWidget item = stepWidgets.removeAt(oldIndex);
          stepWidgets.insert(newIndex, item);
        },
      );
    }

    return Scaffold(
      appBar: AppBar(title: Text("New Recipe")),
      body: Column(
        children: <Widget>[
          Expanded(
            child: ReorderableListView(
              header: Text("Steps"),
              onReorder: _onReorder,
              children: stepWidgets,
            ),
          ),
        ],
      ),
    );
  }
}

RecipeStepWidget 类是(忽略包含):

class RecipeStepWidget extends StatefulWidget {

  RecipeStepWidget({@required Key key}) : super(key: key);

  _RecipeStepWidgetState createState() => _RecipeStepWidgetState();

}

class _RecipeStepWidgetState extends State<RecipeStepWidget> {
  TextEditingController _controller = TextEditingController();
  TextEditingController _durationLowController = TextEditingController();
  TextEditingController _durationHighController = TextEditingController();
  bool concurrent = false;

  RecipeStep toRecipeStep() {
    return RecipeStep(
      text: _controller.text,
    );
  }

  @override
  Widget build(BuildContext context) {
    return Column(
      mainAxisSize: MainAxisSize.min,
      children: <Widget>[
        TextField(
          controller: _controller,
          decoration: InputDecoration(hintText: "Step text"),
        ),
        Row(
          children: <Widget>[
            Text("Duration min: "),
            Container(
              width: 40.0,
              //height: 100.0,
              child: TextField(
                controller: _durationLowController,
                keyboardType: TextInputType.number,
                decoration: InputDecoration(hintText: "0"),
                onChanged: (String val) {
                  if (_durationHighController.text.isEmpty ||
                      int.parse(val) >
                          int.parse(_durationHighController.text)) {
                    _durationHighController.text = val;
                  }
                },
              ),
            ),
            Text(" max: "),
            Container(
              width: 40.0,
              //height: 100.0,
              child: TextField(
                controller: _durationHighController,
                keyboardType: TextInputType.number,
                decoration: InputDecoration(hintText: "0"),
              ),
            ),
          ],
        ),
        Row(
          children: <Widget>[
            Text("Start concurrently with previous step"),
            Checkbox(
                value: concurrent,
                onChanged: (bool val) => {
                      setState(() {
                        concurrent = val;
                      })
                    }),
          ],
        ),
      ],
    );
  }
}

当我编辑 RecipeStateWidgets 中的文本字段或复选框,然后通过单击并拖动它们在列表中重新排列它们时,小部件将重置为其默认状态。

有人知道为什么会这样吗?我认为为了让ReorderableListView 按预期工作,我所要做的就是为其每个孩子设置一个密钥。这不正确吗?

谢谢!

【问题讨论】:

标签: flutter flutter-layout flutter-state


【解决方案1】:

我认为你可以像这样使用 AutomaticKeepAliveClientMixin:

class _RecipeStepWidgetState extends State<RecipeStepWidget> with AutomaticKeepAliveClientMixin  {

  @override
  bool get wantKeepAlive => true;

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2016-09-27
    • 1970-01-01
    • 2020-12-20
    • 1970-01-01
    • 1970-01-01
    • 2011-06-06
    • 2020-06-09
    • 1970-01-01
    相关资源
    最近更新 更多