提问人:learner_bee 提问时间:8/30/2023 最后编辑:learner_bee 更新时间:8/31/2023 访问量:46
如何确定作为参数传递给子小部件的函数的范围?
How to determine the scope of a function passed as a parameter to a child widget?
问:
我正在尝试了解我作为参数传递给子小部件的函数如何能够更新父小部件的实例属性。
例如,以下代码有效:
//...some code
DesignedContainer(
colour: selectedGender == Gender.male
? activeCardColor
: inactiveCardColor,
cardChild: const GenderWidget(
genderIcon: FontAwesomeIcons.mars,
genderName: 'MALE',
),
stateReset: () { //Note this function, I will change this below
setState(() {
selectedGender = Gender.male;
});
},
),
//...some code
class DesignedContainer extends StatefulWidget {
const DesignedContainer({
this.colour = const Color(0xFF1D1E33),
this.cardChild,
this.stateReset,
super.key,
});
final Widget? cardChild;
final Color colour;
final VoidCallback? stateReset;
@override
State<DesignedContainer> createState() => _DesignedContainerState();
}
class _DesignedContainerState extends State<DesignedContainer> {
@override
Widget build(BuildContext context) {
return GestureDetector(
onTap: widget.stateReset, //I shall change this too
child: Container(
margin: const EdgeInsets.all(15.0),
decoration: BoxDecoration(
color: widget.colour,
borderRadius: BorderRadius.circular(10.0),
),
child: widget.cardChild,
),
);
}
}
而如果我更改上面的代码,以便将 setState 移动到 DesignedContainer 小部件,如下所示:
//Inside the parent widget:
stateReset: () => selectedGender = Gender.male,
//some code
//Inside the child widget:
onTap: (){
setState(() {
widget.stateReset!();
});
}
我正在使两个版本都起作用,而后者不起作用。我不明白为什么。
答:
1赞
offworldwelcome
8/31/2023
#1
在第一个版本中,位于有状态小部件中;让我们用关联的 .因此,当您指定:DesignedContainer
MyWidget
MyWidgetState
stateReset: () => setState(...),
指的是 .为什么?setState
MyWidgetState.setState
“闭包是一个函数对象,它可以访问其词法范围内的变量,即使函数在其原始范围之外使用也是如此。函数可以关闭在周围作用域中定义的变量。
来源:https://dart.dev/language/functions#lexical-closures
周围的范围是 的方法。在该作用域中,您可以访问该方法,然后在传递给参数的函数的词法作用域中捕获该方法。build
MyWidgetState
MyWidgetState.setState
stateReset
由于这是可用的,因为即使在函数的原始范围之外使用函数时,词法作用域也可用,因此调用会从其他小部件正确调用。MyWidgetState.setState
在第二个示例中,您调用的是 的 。setState
DesignedContainer.setState
这些是不一样的,第一个重建其关联的小部件,第二个重建 DesignedContainer。
你可以解释为什么在第一种情况下使用相同的原则。
评论
DesignedContainer
stateReset: () => setState(...)
setState
setState
DesignedContainer
DesignedContainer