flutterdartflutter-providerflutter-sharedpreference

Integrate Provider with SharedPreferences to save and get Provider data


The list which stores the task data is integrated with provider for state management, but once I close the app and reopen it again, all tasks vanish. With resources, I got to know about SharedPreferences.

How do I go about saving and getting the data using shared preferences. I have given the code a try, but does not seem to work in my favor.

void saveData() async {
    final prefs = await SharedPreferences.getInstance();
    final String encodedData = Task.encode(tasks);
    await prefs.setString('task_data', encodedData);
  }

  void getData() async {
    final prefs = await SharedPreferences.getInstance();
    final String taskString = prefs.getString('task_data').toString();
    List<Task> tasksData = Task.decode(taskString);
    _tasks = tasksData;
  }

encode() and decode() functions help in mapping List to String and String to List respectively.

static String encode(List<Task> tasks) {
    return jsonEncode(
      tasks.map<Map<String, dynamic>>((task) => Task.toMap(task)).toList(),
    );
  }

  static List<Task> decode(String tasks) {
    var data = (jsonDecode(tasks) as List<dynamic>?);
    if (data != null) {
      return (jsonDecode(tasks) as List<dynamic>?)!.map<Task>((task) {
        return Task.fromJson(task);
      }).toList();
    } else {
      return <Task>[];
    }
  }

The Task list in displayed using ListView.

Widget build(BuildContext context) {
    return Consumer<TaskData>(
      builder: (context, taskData, child) {
        taskData.getData();
        return ListView.builder(
          itemCount: taskData.taskCount,
          itemBuilder: (context, index) {
            taskData.sortTaskList();
            final task = taskData.tasks[index];
            return TaskTile(
              taskTitle: task.name,
              isChecked: task.isDone,
              checkboxCallBack: (checkBoxState) async {
                taskData.upDateTask(task);
                taskData.saveData();
              },
              longPressCallBack: () async {
                taskData.removeTask(task);
                taskData.saveData();
              },
            );
          },
        );
      },
    );
  }

Solution

  • I am expecting that you're using ChangeNotifier with Provider package in TaskData class. In this case you have to add notifyListener() inside getData() because it is async task and you are updating values.

      Future<void> getData() async {
        final prefs = await SharedPreferences.getInstance();
        final String taskString = prefs.getString('task_data').toString();
        List<Task> tasksData = Task.decode(taskString);
        _tasks = tasksData;
        notifyListener(); // Add this line
      }