StatefulWidget 中的 setState() 无法正常工作
setState() within StatefulWidget not working properly
我想做的是,在单击按钮时更改 RawMaterialButton
的颜色。阅读有关 StatefulWidget
的文章,它似乎应该可以工作,但由于某种原因它没有。
flutter: Another exception was thrown: setState() called in constructor: ButtonTest#1a93b(lifecycle state: created, no widget, not mounted)
按钮测试class:
class ButtonState extends StatefulWidget {
@override
State createState() => ButtonTest();
}
class ButtonTest extends State<ButtonState> implements Cipher {
@override
String icon = '';
@override
String title = '';
bool enabled = false;
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(this.title),
),
body: RawMaterialButton(
shape: CircleBorder(side: BorderSide(color: Colors.black)),
fillColor: enabled ? Colors.blue : Colors.red,
onPressed: () {
setState(() {
this.enabled = true;
});
},
padding: EdgeInsets.all(0)),
);
}
}
密码class:
abstract class Cipher {
String icon;
String title;
Widget build(BuildContext context);
}
getCiphers()
getCiphers() {
final List<Cipher> ciphers = new List();
ciphers.add(ButtonTest());
return ciphers;
}
主要class:
void main() => runApp(CipherTools());
class CipherTools extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'CipherTools',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: CipherScreen(
ciphers: getCiphers(),
),
);
}
}
class CipherScreen extends StatelessWidget {
final List<Cipher> ciphers;
CipherScreen({Key key, @required this.ciphers}) : super(key: key);
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text('Ciphers'),
),
body: ListView.builder(
itemCount: ciphers.length,
itemBuilder: (context, index) {
return ListTile(
title: Text(ciphers[index].title),
// When a user taps on the ListTile, navigate to the DetailScreen.
// Notice that we're not only creating a DetailScreen, we're
// also passing the current todo through to it!
onTap: () {
Navigator.push(
context,
MaterialPageRoute(
builder: (context) => DetailScreen(cipher: ciphers[index]),
),
);
},
);
},
),
);
}
}
class DetailScreen extends StatelessWidget {
// Declare a field that holds the Todo
final Cipher cipher;
// In the constructor, require a Todo
DetailScreen({Key key, @required this.cipher}) : super(key: key);
@override
Widget build(BuildContext context) {
return cipher.build(context);
}
}
我做错了什么?
几件事:
ButtonState
应该叫 ButtonTest
因为这是
StatefulWidget
ButtonTest
应该叫 ButtonTestState
因为这是 State
.
然后在 DetailScreen
中,在 build()
方法中,您可以 return StatefulWidget
(ButtonTest
),像这样:
@override
Widget build(BuildContext context) {
return ButtonTest();
}
像这样包装 setState()。
if(this.mounted) {
setState(() {
this.enabled = true;
});
}
我想做的是,在单击按钮时更改 RawMaterialButton
的颜色。阅读有关 StatefulWidget
的文章,它似乎应该可以工作,但由于某种原因它没有。
flutter: Another exception was thrown: setState() called in constructor: ButtonTest#1a93b(lifecycle state: created, no widget, not mounted)
按钮测试class:
class ButtonState extends StatefulWidget {
@override
State createState() => ButtonTest();
}
class ButtonTest extends State<ButtonState> implements Cipher {
@override
String icon = '';
@override
String title = '';
bool enabled = false;
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(this.title),
),
body: RawMaterialButton(
shape: CircleBorder(side: BorderSide(color: Colors.black)),
fillColor: enabled ? Colors.blue : Colors.red,
onPressed: () {
setState(() {
this.enabled = true;
});
},
padding: EdgeInsets.all(0)),
);
}
}
密码class:
abstract class Cipher {
String icon;
String title;
Widget build(BuildContext context);
}
getCiphers()
getCiphers() {
final List<Cipher> ciphers = new List();
ciphers.add(ButtonTest());
return ciphers;
}
主要class:
void main() => runApp(CipherTools());
class CipherTools extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'CipherTools',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: CipherScreen(
ciphers: getCiphers(),
),
);
}
}
class CipherScreen extends StatelessWidget {
final List<Cipher> ciphers;
CipherScreen({Key key, @required this.ciphers}) : super(key: key);
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text('Ciphers'),
),
body: ListView.builder(
itemCount: ciphers.length,
itemBuilder: (context, index) {
return ListTile(
title: Text(ciphers[index].title),
// When a user taps on the ListTile, navigate to the DetailScreen.
// Notice that we're not only creating a DetailScreen, we're
// also passing the current todo through to it!
onTap: () {
Navigator.push(
context,
MaterialPageRoute(
builder: (context) => DetailScreen(cipher: ciphers[index]),
),
);
},
);
},
),
);
}
}
class DetailScreen extends StatelessWidget {
// Declare a field that holds the Todo
final Cipher cipher;
// In the constructor, require a Todo
DetailScreen({Key key, @required this.cipher}) : super(key: key);
@override
Widget build(BuildContext context) {
return cipher.build(context);
}
}
我做错了什么?
几件事:
ButtonState
应该叫ButtonTest
因为这是StatefulWidget
ButtonTest
应该叫ButtonTestState
因为这是State
.
然后在 DetailScreen
中,在 build()
方法中,您可以 return StatefulWidget
(ButtonTest
),像这样:
@override
Widget build(BuildContext context) {
return ButtonTest();
}
像这样包装 setState()。
if(this.mounted) {
setState(() {
this.enabled = true;
});
}