我使用提供程序和更改通知程序,问题是当我更改状态并在同一文件中通知侦听器时,用户界面已更新,但是当我尝试从另一个屏幕中的模型访问相同数据时,它仍然保持原始或第一个版本,而不是更新的版本,另一个文件中的类甚至使用更改通知程序提供程序和使用者,就像其中包含模态类的文件但不更改值一样,它仅保留初始值,第二个该文件仅具有changenotifierprovider和consumer,但仅显示初始文件而不显示已更新的文件,而是显示具有模型类的第一个文件,并且更改通知程序功能在其小部件中显示更新的版本
这是我的第二个屏幕,即使在第一个屏幕中更新了初始状态,它也只显示初始状态
import 'package:flutter/material.dart';
import 'package:hotel_search/common/theme.dart';
import 'package:hotel_search/sliding_bottom_sheet_content.dart';
import 'package:hotel_search/home_page.dart';
import 'package:provider/provider.dart';
class BookScreen extends StatefulWidget {
@override
_BookScreenState createState() => _BookScreenState();
}
class _BookScreenState extends State<BookScreen> {
@override
void initState() {
super.initState();
/*Future.delayed(Duration(milliseconds: 1000)).then((v) {
Navigator.pop(context);
});*/
}
@override
Widget build(BuildContext context) {
final themeData = HotelConceptThemeProvider.get();
return ChangeNotifierProvider<MyModel>(
create: (context) => MyModel(),
child: MaterialApp(
home: Scaffold(
backgroundColor: Colors.grey[50],
appBar: AppBar(
leading: IconButton(
icon: Icon(Icons.arrow_back, color: Colors.black),
onPressed: () => Navigator.of(context).pop(),
),
elevation: 0,
titleSpacing: 0,
backgroundColor: Colors.white,
title: Text(' ',
style: TextStyle(
color: Colors.black,
fontFamily: 'Montserrat',
fontSize: 20,
))),
body: SingleChildScrollView(
child: ConstrainedBox(
constraints: BoxConstraints(
minHeight: MediaQuery.of(context).size.height,
),
child: Column(
mainAxisSize: MainAxisSize.min,
mainAxisAlignment: MainAxisAlignment.start,
crossAxisAlignment: CrossAxisAlignment.center,
children: <Widget>[
SizedBox(
height: 40,
),
Container(
width: MediaQuery.of(context).size.width - 100,
height: 100,
child: Image.asset(
"assets/images/brand.png",
width: 0,
height: 0,
fit: BoxFit.cover,
)),
Divider(
height: 25,
color: Colors.grey[300],
),
Container(
padding:
EdgeInsets.only(left: 20, top: 20, bottom: 20),
width: MediaQuery.of(context).size.width,
child: Text('Review \nYour Booking',
style: TextStyle(
color: Colors.black,
fontFamily: 'Montserrat',
fontSize: 30,
))),
Divider(
height: 25,
color: Colors.grey[300],
),
Container(
padding: EdgeInsets.only(left: 20, top: 20),
width: MediaQuery.of(context).size.width,
child: Text("HOTEL NAME",
style: TextStyle(
fontFamily: 'Montserrat',
fontSize: 20,
fontWeight: FontWeight.w700,
))),
Row(children: <Widget>[
Consumer<MyModel>(
builder: (context, myModel, children) {
return Container(
height: 100,
child: Column(
mainAxisAlignment: MainAxisAlignment.start,
children: <Widget>[
Container(
padding:
EdgeInsets.only(left: 20, top: 5),
width: 200,
child: Text(
myModel.datesChosen.toString(),
style: TextStyle(
fontSize: 13,
fontFamily: 'Montserrat',
))),
Container(
padding:
EdgeInsets.only(left: 20, top: 5),
width: 200,
child: Text(myModel.roomtype.toString(),
style: TextStyle(
fontSize: 13,
fontFamily: 'Montserrat',
)),
),
Container(
padding:
EdgeInsets.only(left: 20, top: 5),
width: 200,
child: Text("CHECK IN AND OUT TIME",
style: TextStyle(
fontSize: 13,
fontFamily: 'Montserrat',
))),
Container(
padding:
EdgeInsets.only(left: 20, top: 5),
width: 200,
child: Text("TYPE OF ROOM CHOSEN",
style: TextStyle(
fontSize: 13,
fontFamily: 'Montserrat',
)))
]));
}),
Spacer(),
Container(
margin: EdgeInsets.only(right: 20),
width: 150,
height: 120,
decoration: BoxDecoration(
image: DecorationImage(
image: AssetImage("img/card.jpg"),
fit: BoxFit.cover),
color: Colors.grey[300],
shape: BoxShape.rectangle,
borderRadius: BorderRadius.circular(10),
boxShadow: [
BoxShadow(
color: Colors.grey.withOpacity(0.2),
spreadRadius: 2,
blurRadius: 5,
offset: Offset(
0, 3), // changes position of shadow
)
]))
]),
SizedBox(height: 60),
Divider(
height: 25,
color: Colors.grey[300],
),
SizedBox(height: 20),
Container(
color: Color(0xff008d4b),
height: 60,
width: MediaQuery.of(context).size.width - 50,
child: FlatButton(
onPressed: () {
/*...*/
},
child: Text(
"Book Now",
style: TextStyle(
color: Colors.white,
fontFamily: 'Montserrat',
fontSize: 20,
),
),
),
)
]),
)))));
}
}
这是我创建changenotifier的第一个部分,虽然还有很多,但是很长,所以我刚刚添加了这一部分,但是这里的所有小部件都显示了更新状态
class MyModel with ChangeNotifier{
String datesChosen = "Click here";
String checkin;
String checkout;
String email;
String name;
String roomtype = "Click here";
String phonenumber;
String hotelname;
void updateData1 (data){
datesChosen = data;
print(datesChosen);
notifyListeners();
}
void updateData2 (data){
roomtype = data;
print(roomtype);
notifyListeners();
}
答案 0 :(得分:0)
您正在使用的第二个屏幕
ChangeNotifierProvider<MyModel>(
create: (context) => MyModel(),
....
)
,这意味着您实际上是在创建一个新模型,而不是重用第一页中的一个(它们是无关的,更改一个不会更改另一个),我不知道您如何称呼第二个屏幕,因此这更具推测性,但是您将模型从上一个屏幕传递到第二个屏幕,然后使用ChangeNotifierProvider<MyModel>.value()
,它将注册相同的模型并在发生更改时通知两个页面
在第一个屏幕
onTap: Navigator.of(context).push(
MaterialPageRoute(
builder: BookScreen(Provider.of<MyModel>(context, listen: false))
)
);
现在在第二个屏幕
class BookScreen extends StatefulWidget {
final MyModel model;
BookScreen(this.model);
@override
_BookScreenState createState() => _BookScreenState();
}
class _BookScreenState extends State<BookScreen> {
@override
void initState() {
super.initState();
/*Future.delayed(Duration(milliseconds: 1000)).then((v) {
Navigator.pop(context);
});*/
}
@override
Widget build(BuildContext context) {
final themeData = HotelConceptThemeProvider.get();
return ChangeNotifierProvider<MyModel>.value(
value: widget.model,
....
)
很明显,如果您在应用程序的开头(在第一个MaterialApp之上)创建了提供程序MyModel,则不需要所有这些逻辑,而可以在任何地方使用它