プロンプト
FlutterでTodoアプリを実装してください
回答
Flutterを使用してToDoアプリを実装するための基本的なステップを示します。以下の手順に従ってください。
-
Flutterプロジェクトのセットアップ:
flutter create todo_app
-
プロジェクトに必要な依存関係を追加します。
pubspec.yaml
ファイルを編集し、flutter/material.dart
とprovider
パッケージを追加します。dependencies: flutter: sdk: flutter provider: ^5.0.0
-
ToDoアイテムを表すモデルを作成します。
lib/models/todo.dart
を作成し、以下のコードを追加します。class Todo { final String title; final bool isDone; Todo({required this.title, this.isDone = false}); }
-
ToDoリストの状態を管理するプロバイダーを作成します。
lib/providers/todo_provider.dart
を作成し、以下のコードを追加します。import 'package:flutter/material.dart'; import 'package:todo_app/models/todo.dart'; class TodoProvider extends ChangeNotifier { List<Todo> _todos = []; List<Todo> get todos => _todos; void addTodo(String title) { _todos.add(Todo(title: title)); notifyListeners(); } void toggleTodoStatus(int index) { _todos[index].isDone = !_todos[index].isDone; notifyListeners(); } }
-
メインのToDoアプリケーションを作成します。
lib/main.dart
を編集し、以下のコードを追加します。import 'package:flutter/material.dart'; import 'package:provider/provider.dart'; import 'package:todo_app/providers/todo_provider.dart'; void main() { runApp(TodoApp()); } class TodoApp extends StatelessWidget { @override Widget build(BuildContext context) { return ChangeNotifierProvider( create: (context) => TodoProvider(), child: MaterialApp( title: 'Todo App', home: TodoScreen(), ), ); } } class TodoScreen extends StatelessWidget { @override Widget build(BuildContext context) { final provider = Provider.of<TodoProvider>(context); return Scaffold( appBar: AppBar( title: Text('Todo List'), ), body: ListView.builder( itemCount: provider.todos.length, itemBuilder: (context, index) { final todo = provider.todos[index]; return ListTile( title: Text(todo.title), leading: Checkbox( value: todo.isDone, onChanged: (_) { provider.toggleTodoStatus(index); }, ), ); }, ), floatingActionButton: FloatingActionButton( onPressed: () { // ダイアログを表示して新しいToDoを追加 showDialog( context: context, builder: (context) { final TextEditingController controller = TextEditingController(); return AlertDialog( title: Text('Add Todo'), content: TextField( controller: controller, decoration: InputDecoration(hintText: 'Enter todo title'), ), actions: [ TextButton( onPressed: () { Navigator.pop(context); }, child: Text('Cancel'), ), TextButton( onPressed: () { provider.addTodo(controller.text); Navigator.pop(context); }, child: Text('Add'), ), ], ); }, ); }, child: Icon(Icons.add), ), ); } }
これで、ToDoアプリが実装されました。アプリを実行して、ToDoリストにアイテムを追加し、完了/未完了のステータスを切り替えることができます。
実際にやってみる
Flutter\todo_app\pubspec.yaml
# Dependencies specify other packages that your package needs in order to work.
# To automatically upgrade your package dependencies to the latest versions
# consider running `flutter pub upgrade --major-versions`. Alternatively,
# dependencies can be manually updated by changing the version numbers below to
# the latest version available on pub.dev. To see which dependencies have newer
# versions available, run `flutter pub outdated`.
dependencies:
flutter:
sdk: flutter
provider: ^5.0.0
lib
以下を↓のように編集
lib
│ main.dart
│
├─models
│ todo.dart
│
└─providers
todo_provider.dart
何度かエラーが出たのでエラーログをAIに読ませてコードを何度か再生成
Flutter\todo_app\lib\models\todo.dart
class Todo {
String title;
bool isDone;
Todo({
required this.title,
this.isDone = false,
});
void toggleDone() {
isDone = !isDone;
}
}
Flutter\todo_app\lib\providers\todo_provider.dart
import 'package:flutter/material.dart';
import 'package:todo_app/models/todo.dart';
class TodoProvider extends ChangeNotifier {
List<Todo> _todos = [];
List<Todo> get todos => _todos;
void addTodo(String title) {
_todos.add(Todo(title: title));
notifyListeners();
}
void toggleTodoStatus(int index) {
_todos[index].toggleDone(); // Todoモデルのメソッドを呼び出し、isDoneをトグルします
notifyListeners();
}
}
Flutter\todo_app\lib\main.dart
import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
import 'package:todo_app/providers/todo_provider.dart'; // Import your TodoProvider
void main() {
runApp(TodoApp());
}
class TodoApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return ChangeNotifierProvider(
create: (context) => TodoProvider(), // Instantiate TodoProvider here
child: MaterialApp(
title: 'Todo App',
home: TodoScreen(),
),
);
}
}
class TodoScreen extends StatelessWidget {
@override
Widget build(BuildContext context) {
// Obtain an instance of TodoProvider using Provider.of
final provider = Provider.of<TodoProvider>(context);
return Scaffold(
appBar: AppBar(
title: Text('Todo List'),
),
body: ListView.builder(
itemCount: provider.todos.length,
itemBuilder: (context, index) {
final todo = provider.todos[index];
return ListTile(
title: Text(todo.title),
leading: Checkbox(
value: todo.isDone,
onChanged: (_) {
provider.toggleTodoStatus(index);
},
),
);
},
),
floatingActionButton: FloatingActionButton(
onPressed: () {
// Show a dialog to add a new todo
showDialog(
context: context,
builder: (context) {
final TextEditingController controller = TextEditingController();
return AlertDialog(
title: Text('Add Todo'),
content: TextField(
controller: controller,
decoration: InputDecoration(hintText: 'Enter todo title'),
),
actions: [
TextButton(
onPressed: () {
Navigator.pop(context);
},
child: Text('Cancel'),
),
TextButton(
onPressed: () {
provider.addTodo(controller.text);
Navigator.pop(context);
},
child: Text('Add'),
),
],
);
},
);
},
child: Icon(Icons.add),
),
);
}
}