首页 > 解决方案 > 如何在我的 Note 应用程序中实现提供程序,特别是 ChangeNotifierProvider 实现

问题描述

我是学习提供者,想在我的简单笔记应用程序中实现它。我浏览了文档,查看了有关提供程序实现的 youtube 视频和 Medium 文章,我理解了这个概念(我认为),但我仍然对如何在我的项目中实现它感到有些困惑。在过去的 1 周里,我陷入了困境,任何参考/建议都会对我有很大帮助。

这是我的 main.dart 代码

import 'package:flutter/material.dart';
import 'package:note_taking_app/ui/main_screen.dart';

void main() async {
  WidgetsFlutterBinding.ensureInitialized();
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: MainScreen(),
      debugShowCheckedModeBanner: false,
    );
  }
}

这是我显示创建的笔记的地方

import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:note_taking_app/constants/buttons_and_icons_misc(classes).dart';
import 'package:note_taking_app/constants/text_and_decorations(methods).dart';
import 'package:note_taking_app/db/model_notes.dart';
import 'package:note_taking_app/ui/adding_notes.dart';

class MainScreen extends StatefulWidget {
  @override
  _MainScreenState createState() => _MainScreenState();
}

class _MainScreenState extends State<MainScreen> {
  List<Note> noteList = [];

  @override
  void initState() {
    super.initState();
    dbHelper.initDatabase();
    setNotesFromDB();
  }

  setNotesFromDB() async {
    print("Entered setNotes in main page");
    var fetchedNotes = await dbHelper.getNotesFromDB();
    setState(() {
      noteList = fetchedNotes;
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: mainScreenAppBar,
      floatingActionButton: FAB(
        whatToDo: () {
          gotoAddingNotesPage(context);
        },
      ),
      body: SafeArea(
        child: ListView.builder(
          itemCount: noteList.length,
          itemBuilder: (context, index) {
            return TileCard(
              titleText: ('${noteList[index].title}'),
              dateText: ('${noteList[index].date}'),
              whatToDoOnPressed: (){
                openUserClickedNote();
                debugPrint('${noteList[index].id}');
              },
            );
          },
        ),
      ),
    );
  }
  gotoAddingNotesPage(BuildContext context) {
    Navigator.push(
      context,
      MaterialPageRoute(builder: (context) => AddingNotes()),
    ).then((value) => setState(() {
          setNotesFromDB();
        }));
  }
  openUserClickedNote() async {
    var getNoteByID = await dbHelper.queryRows('$noteList[index].id');
  }
}

这是AddingNote类,我在这里添加了ChangeNotifier和notifyListeners

import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:intl/intl.dart';
import 'package:note_taking_app/constants/buttons_and_icons_misc(classes).dart';
import 'package:note_taking_app/db/db_operations.dart';
import 'package:note_taking_app/db/model_notes.dart';

final bodyController = TextEditingController();
final headerController = TextEditingController();
final dbHelper = DatabaseHelper.instance;
String formattedDate = DateFormat.yMMMd('en_US').format(DateTime.now());

class AddingNotes extends StatefulWidget {
  @override
  _AddingNotesState createState() => _AddingNotesState();
}

class _AddingNotesState extends State<AddingNotes> with ChangeNotifier {
  @override
  void initState() {
    super.initState();
    bodyController.clear();
    headerController.clear();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        elevation: 0,
        backwardsCompatibility: true,
        leading: LeadingIcon(
          callBack: () {
            Navigator.pop(context);
          },
        ),
        backgroundColor: Colors.white.withOpacity(0.4),
        actions: <Widget>[
          ActionsIconButton(
            icon: Icon(save, color: black),
            callBack: () async {
              String title = headerController.text;
              String body = bodyController.text;
              Note note = Note(20, title, body, formattedDate);

              var value = await dbHelper.insert(note);
              print("if 1 is return then insert success and 0 then not inserted : $value");
              notifyListeners();

              Navigator.pop(context);
            },
          )
        ],
      ),
      body: Container(
        color: Colors.white.withOpacity(0.4),
        child: Padding(
          padding: const EdgeInsets.all(13.0),
          child: Column(
            children: [
              HeaderBody(
                textEditingController: headerController,
              ),
              SizedBox(
                height: 32.0,
              ),
              Expanded(
                child: NotesBody(
                  textEditingController: bodyController,
                ),
              ),
            ],
          ),
        ),
      ),
    );
  }
}

这是 Notes 模型类

import 'db_operations.dart';

class Note {
  int id;
  String title;
  String body;
  String date;

  Note(this.id, this.title, this.body, this.date);

  Note.fromMap(Map<String, dynamic> map) {
    id = map['id'];
    title = map['title'];
    body = map['body'];
    date = map['date'];
  }

  Map<String, dynamic> toMap() {
    return {
      DatabaseHelper.columnId: id,
      DatabaseHelper.columnTitle: title,
      DatabaseHelper.columnBody: body,
      DatabaseHelper.columnDate: date,
    };
  }

  @override
  String toString() {
    return '$title, $date';
  }
}

标签: flutterflutter-providerstate-managementflutter-change-notifierprovider-model

解决方案


提供者示例:

class NotesProvider extends ChangeNotifier {
  List<NotesData> _notesList = [];

  UnmodifiableListView<NotesData> get notes {
    return UnmodifiableListView(_notesList);
  }

  int get notesCount {
    return _notesList.length;
  }

  void addNotes({ResNotesModel data}) {
    _notesList.addAll(data.data);
    notifyListeners();
  }

  void updatePinNote({int id, int isPinned}) {
    _notesList[_notesList.indexWhere((element) => element.id == id)].isPinned =
        isPinned;
    notifyListeners();
  }

}

要访问提供者的属性,您需要使用 multiprovider 包装材料应用程序。

return MultiProvider(
  providers: [
    ChangeNotifierProvider(create: (context) => NotesProvider()),   
  ],
  child: MaterialApp(
    home: MainScreen(),
    debugShowCheckedModeBanner: false,
  ),
);

然后您可以使用消费者在其他屏幕中使用

Consumer<NotesProvider>(
        builder: (context, notesData, child) => Text("data")
)

推荐阅读