Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/dart/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Dart 颤振列表视图显示错误的项目_Dart_Flutter - Fatal编程技术网

Dart 颤振列表视图显示错误的项目

Dart 颤振列表视图显示错误的项目,dart,flutter,Dart,Flutter,列表视图显示项目1、项目2和项目3。 当我试图删除Item2时,ListView错误地显示Item1和Item2。 控制台显示列表中的正确项:Item1和Item3 主屏幕: class HomeScreen extends StatefulWidget { @override HomeScreenState createState() => new HomeScreenState(); } class HomeScreenState extends State<H

列表视图显示项目1、项目2和项目3。 当我试图删除Item2时,ListView错误地显示Item1和Item2。 控制台显示列表中的正确项:Item1和Item3

主屏幕:

    class HomeScreen extends StatefulWidget {
  @override
  HomeScreenState createState() => new HomeScreenState();
}

class HomeScreenState extends State<HomeScreen> {
  List<Todo> todos = new List();

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

  void populateTodos() async {
    TodoDatabase db = new TodoDatabase();
    db.getAllTodos().then((newTodos) {
      for (var todo in newTodos) {
        print(todo.title + ", " + todo.id);
      }
      setState(() => todos = newTodos);
    });
  }

  void openAddTodoScreen() async {
    Navigator
        .push(context,
            new MaterialPageRoute(builder: (context) => new AddTodoScreen()))
        .then((b) {
      populateTodos();
    });
  }

  void clearDb() async {
    TodoDatabase db = new TodoDatabase();
    db.clearDb();
    populateTodos();
  }

  @override
  Widget build(BuildContext context) {
    return new Scaffold(
      appBar: new AppBar(
        title: new Text("Todo App"),
        actions: <Widget>[
          new IconButton(
            icon: new Icon(Icons.delete),
            onPressed: () => clearDb(),
          ),
          new IconButton(
            icon: new Icon(Icons.refresh),
            onPressed: () => populateTodos(),
          )
        ],
      ),
      body: new Center(
        child: new Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: <Widget>[
            new Expanded(
              child: new ListView.builder(
                padding: new EdgeInsets.all(10.0),
                itemCount: todos.length,
                itemBuilder: (BuildContext context, int index) {
                  return new TodoItem(todos[index], onDelete: (id) {
                    TodoDatabase db = new TodoDatabase();
                    print("ID: " + id);
                    db.deleteTodo(id).then((b) {
                      populateTodos();
                    });
                  });
                },
              ),
            )
          ],
        ),
      ),
      floatingActionButton: new FloatingActionButton(
          child: new Icon(Icons.add), onPressed: () => openAddTodoScreen()),
    );
  }
}
类主屏幕扩展StatefulWidget{
@凌驾
HomeScreenState createState()=>新HomeScreenState();
}
类HomeScreenState扩展状态{
列表待办事项=新建列表();
@凌驾
void initState(){
super.initState();
populateTodos();
}
void populateTodos()异步{
TodoDatabase db=新的TodoDatabase();
db.getAllTodos().then((newTodos){
for(在newTodos中为var todo){
打印(todo.title+”,“+todo.id);
}
设置状态(()=>todos=newTodos);
});
}
void openAddTodoScreen()异步{
领航员
.push(上下文),
new MaterialPage路由(生成器:(上下文)=>new AddTodoScreen())
.然后((b){
populateTodos();
});
}
void clearDb()异步{
TodoDatabase db=新的TodoDatabase();
db.clearDb();
populateTodos();
}
@凌驾
小部件构建(构建上下文){
归还新脚手架(
appBar:新的appBar(
标题:新文本(“Todo应用程序”),
行动:[
新图标按钮(
图标:新图标(图标。删除),
onPressed:()=>clearDb(),
),
新图标按钮(
图标:新图标(图标。刷新),
onPressed:()=>populateTodos(),
)
],
),
正文:新中心(
子:新列(
mainAxisAlignment:mainAxisAlignment.center,
儿童:[
新扩展(
子项:新建ListView.builder(
填充:新边缘设置。全部(10.0),
itemCount:todos.length,
itemBuilder:(构建上下文,int索引){
返回新的TodoItem(todos[index],onDelete:(id){
TodoDatabase db=新的TodoDatabase();
打印(“ID:+ID”);
db.deleteTodo(id).然后((b){
populateTodos();
});
});
},
),
)
],
),
),
floatingActionButton:新的floatingActionButton(
子:新图标(Icons.add),按下时:()=>openAddTodoScreen()),
);
}
}
数据库代码:

    class TodoDatabase {
  TodoDatabase();
  static Database _db;

  Future<Database> get db async {
    if (_db != null) {
      return _db;
    }
    _db = await initDB();
    return _db;
  }

  Future<Database> initDB() async {
    Directory documentsDirectory = await getApplicationDocumentsDirectory();
    String path = join(documentsDirectory.path, "main.db");
    var theDb = await openDatabase(path, version: 1, onCreate: createDatabase);
    return theDb;
  }

  void createDatabase(Database db, int version) async {
    await db.execute("CREATE TABLE Todos(id STRING PRIMARY KEY, title TEXT, description TEXT)");

    print("Database was Created!");
  }

  Future<List<Todo>> getAllTodos() async {
    var dbClient = await db;
    List<Map> res = await dbClient.query("Todos");
    print(res);
    return res.map((map) => new Todo(title: map["title"], description: map["description"], id: map["id"])).toList();
  }

  Future<Todo> getTodo(String id) async {
    var dbClient = await db;
    var res = await dbClient.query("Todos", where: "id = ?", whereArgs: [id]);
    if (res.length == 0) return null;
    return new Todo.fromDb(res[0]);
  }

  Future<int> addTodo(Todo todo) async {
    var dbClient = await db;
    int res = await dbClient.insert("Todos", todo.toMap());
    return res;
  }

  Future<int> updateTodo(Todo todo) async {
    var dbClient = await db;
    int res = await dbClient.update(
      "Todos",
      todo.toMap(),
      where: "id = ?",
      whereArgs: [todo.id]);
      return res;
  }

  Future<int> deleteTodo(String id) async {
    var dbClient = await db;
    var res = await dbClient.delete(
      "Todos",
      where: "id = ?",
      whereArgs: [id]);
      print("Deleted item");
      return res;
  }

  Future<int> clearDb() async {
    var dbClient = await db;
    var res = await dbClient.execute("DELETE from Todos");
      print("Deleted db contents");
      return res;
  }
}
类TodoDatabase{
TodoDatabase();
静态数据库;
未来获取数据库异步{
如果(_db!=null){
返回_db;
}
_db=等待initDB();
返回_db;
}
Future initDB()异步{
目录文档Directory=await getApplicationDocumentsDirectory();
stringpath=join(documentsDirectory.path,“main.db”);
var theDb=wait openDatabase(路径,版本:1,onCreate:createDatabase);
返回theDb;
}
void createDatabase(数据库数据库数据库,int版本)异步{
wait db.execute(“创建表TODO(id字符串主键、标题文本、描述文本)”);
打印(“已创建数据库!”);
}
将来的getAllTodos()异步{
var dbClient=await db;
List res=await dbClient.query(“TODO”);
印刷品(res);
return res.map((map)=>newtodo(title:map[“title”]、description:map[“description”]、id:map[“id”])。toList();
}
将来的getTodo(字符串id)异步{
var dbClient=await db;
var res=await dbClient.query(“Todos”,其中:“id=?”,wherergs:[id]);
if(res.length==0)返回null;
从数据库(res[0])返回新的Todo.fromDb;
}
Future addTodo(Todo-Todo)异步{
var dbClient=await db;
int res=await dbClient.insert(“Todos”,todo.toMap());
返回res;
}
将来的updateTodo(Todo Todo)异步{
var dbClient=await db;
int res=await dbClient.update(
“待办事项”,
todo.toMap(),
其中:“id=?”,
wherergs:[todo.id]);
返回res;
}
未来删除TODO(字符串id)异步{
var dbClient=await db;
var res=await dbClient.delete(
“待办事项”,
其中:“id=?”,
wherergs:[id]);
打印(“删除项”);
返回res;
}
未来的clearDb()异步{
var dbClient=await db;
var res=await dbClient.execute(“从TODO中删除”);
打印(“已删除的数据库内容”);
返回res;
}
}
这几乎像是一只扑动的虫子。 我必须添加更多的文本,否则它将不允许我发布。 我不知道如何进一步说明这个问题。 谢谢你的帮助

我丢了一把钥匙。 以下是正确的ListView.builder:

    new ListView.builder(
    key: new Key(randomString(20)),
    padding: new EdgeInsets.all(10.0),
    itemCount: todos.length,
    itemBuilder: (BuildContext context, int index) {
        return new TodoItem(todos[index], onDelete: (id) {
            TodoDatabase db = new TodoDatabase();
            db.deleteTodo(id).then((b) {
            populateTodos();
            });
        });
    },
),

是的,修好了。谢谢您还可以对密钥使用“UniqueKey()”