问题描述
我正在使用Flutter。我有一个带有3个标签的简单应用。每个带有ListView的选项卡中都有一个RefreshIndicator。这些行是用另一种方法构建的。
这是代码:
@override
小部件构建(BuildContext上下文){
最后的GlobalKey< RefreshIndicatorState> _RIKey1 = new GlobalKey< RefreshIndicatorState>();
final GlobalKey< RefreshIndicatorState> _RIKey2 = new GlobalKey< RefreshIndicatorState>();
final GlobalKey< RefreshIndicatorState> _RIKey3 = new GlobalKey< RefreshIndicatorState>();
debugPrint(_RIKey1.toString());
debugPrint(_RIKey2.toString());
debugPrint(_RIKey3.toString());
返回新的Scaffold(
主体:new DefaultTabController(
长度:3,
子代:new Scaffold(
appBar:new AppBar(
bottom:new TabBar(
标签:[
新标签(icon:新Icon(Icons.view_list))),
新标签(icon:new Icon(Icons.hotel)),
新Tab(icon:new Icon(Icons.assesssmentment)),
],
),
title:new Text('Data'),
),
body :新的TabBarView(
子项:[
新的RefreshIndicator(
项:_RIKey1,
onRefresh:_actualizoData,
子项:new ListView.builder(
padding :new EdgeInsets.only(top:5.0),
itemCount:linea_reservas.length * 2,
itemBuilder:(BuildContext上下文,int位置){
if(positi on.isOdd)返回新的Divider();
最终索引=位置〜/ 2;
return _buildRow(index);
}),
),
新的RefreshIndicator(
键:_RIKey2,
onRefresh:_actualizoData,
子级:new ListView.builder(
填充:new EdgeInsets.only(顶部:8.0),
itemCount:linea_inouthouse.length * 2,
itemBuilder:(BuildContext上下文,int position){
if(position.isOdd)return new Divider();
最终索引=位置〜/ 2;
return _buildRowInOutHouse(index);
}),
),
新RefreshIndicator(
键:_RIKey3,
刷新:_actualizoData,
子级:new ListView.builder(
padding:new EdgeInsets.only(top:5.0),
itemCount:linea_ocupacion.length * 2,
它emBuilder:(BuildContext context,int position){
if(position.isOdd)返回新的Divider();
最终索引=位置〜/ 2;
return _buildRowOcupacion(index);
}),
),
],
),
),
),
);
}
我添加了debugPrints,输出为6行,而不是3行
I / flutter(5252):[LabeledGlobalKey< RefreshIndicatorState>#4d76c]
I / flutter(5252) :[LabeledGlobalKey< RefreshIndicatorState>#59b9e]
I / flutter(5252):[LabeledGlobalKey< RefreshIndicatorState>#2c88b]
I / flutter(5252):[LabeledGlobalKey< RefreshIndicatorStateb&d] 42 b I / Flutter(5252):[LabeledGlobalKey< RefreshIndicatorState>#1c984]
I / flutter(5252):[LabeledGlobalKey< RefreshIndicatorState&#; $ p>
该应用程序正常运行,但是几次更改标签后,它因以下错误而崩溃:
I / flutter(5252):W小工具库引起的异常CA ══════════════════════════════════════
I / flutter(5252):引发断言之后,构建NotificationListener< KeepAliveNotification&g t;:
I / flutter(5252):多个小部件使用了相同的GlobalKey。
I / flutter(5252):键[LabeledGlobalKey< RefreshIndicatorState>#7bd42]被多个小部件使用。
I / flutter(5252)的父母:这些小部件是:
I / flutter(5252):-RepaintBoundary-[< [LabeledGlobalKey< RefreshIndicatorState>#7bd42]>](renderObject:
I / flutter(5252):RenderRepaintBoundary#60a4a分离)
I / flutter(5252):-RepaintBoundary-[< [LabeledGlobalKey< RefreshIndicatorState>#7bd42]>](renderObject:
I / flutter(5252):RenderRepaintBoundary#c8cdb NEEDS-LAYOUT NEEDS-PAINT)
I / flutter(5252):只能在小部件树中一次在一个小部件上指定GlobalKey。
键是在Build方法中生成的,所以,我不明白为什么多个小部件使用了相同的GlobalKey
错误
为什么再次生成密钥,为什么它不是唯一的?我并不是在说一千个意图,在选项卡之间切换4或5次后,错误就会出现。
谢谢您的帮助。
解决方案您可以手动创建密钥并使用静态/常量值吗?例如...
import‘package:flutter / widgets.dart’;
类RIKeys {
static final riKey1 = const Key(’__ RIKEY1__’);
static final riKey2 = const Key(’__ RIKEY2__’);
static final riKey3 = const Key(’__ RIKEY3__’);
}
然后在...
正文:new TabBarView(
子级:[
new RefreshIndicator(new RefreshIndicator(
// //使用手动静态值代替...
键:RIKeys.riKey1,
刷新:_actualizoData,
子级:new ListView.builder(
padding:new EdgeInsets.only(top:5.0),
itemCount :linea_reservas.length * 2,
itemBuilder:(BuildContext上下文,int position){
if(position.isOdd)return new Divider();
final index = position〜/ 2;
return _buildRow(index);
}),
),
我在类似情况下也取得了一些成功……尤其是在redux或其他类似模式下……
I'm using Flutter. I have a simple app with 3 tabs. There is a RefreshIndicator in each tab with a ListView. The rows are built in another method.This is the code:
@override
Widget build(BuildContext context) {
final GlobalKey<RefreshIndicatorState> _RIKey1 = new GlobalKey<RefreshIndicatorState>();
final GlobalKey<RefreshIndicatorState> _RIKey2 = new GlobalKey<RefreshIndicatorState>();
final GlobalKey<RefreshIndicatorState> _RIKey3 = new GlobalKey<RefreshIndicatorState>();
debugPrint(_RIKey1.toString());
debugPrint(_RIKey2.toString());
debugPrint(_RIKey3.toString());
return new Scaffold(
body: new DefaultTabController(
length: 3,
child: new Scaffold(
appBar: new AppBar(
bottom: new TabBar(
tabs: [
new Tab(icon: new Icon(Icons.view_list)),
new Tab(icon: new Icon(Icons.hotel)),
new Tab(icon: new Icon(Icons.assessment)),
],
),
title: new Text('Data'),
),
body: new TabBarView(
children: [
new RefreshIndicator(
key: _RIKey1,
onRefresh: _actualizoData,
child: new ListView.builder(
padding: new EdgeInsets.only(top: 5.0),
itemCount: linea_reservas.length * 2,
itemBuilder: (BuildContext context, int position) {
if (position.isOdd) return new Divider();
final index = position ~/ 2;
return _buildRow(index);
}),
),
new RefreshIndicator(
key: _RIKey2,
onRefresh: _actualizoData,
child: new ListView.builder(
padding: new EdgeInsets.only(top: 8.0),
itemCount: linea_inouthouse.length * 2,
itemBuilder: (BuildContext context, int position) {
if (position.isOdd) return new Divider();
final index = position ~/ 2;
return _buildRowInOutHouse(index);
}),
),
new RefreshIndicator(
key: _RIKey3,
onRefresh: _actualizoData,
child: new ListView.builder(
padding: new EdgeInsets.only(top: 5.0),
itemCount: linea_ocupacion.length * 2,
itemBuilder: (BuildContext context, int position) {
if (position.isOdd) return new Divider();
final index = position ~/ 2;
return _buildRowOcupacion(index);
}),
),
],
),
),
),
);
}
I'd added the debugPrints and the output are 6 lines, instead of 3.
I/flutter ( 5252): [LabeledGlobalKey<RefreshIndicatorState>#4d76c]
I/flutter ( 5252): [LabeledGlobalKey<RefreshIndicatorState>#59b9e]
I/flutter ( 5252): [LabeledGlobalKey<RefreshIndicatorState>#2c88b]
I/flutter ( 5252): [LabeledGlobalKey<RefreshIndicatorState>#7bd42]
I/flutter ( 5252): [LabeledGlobalKey<RefreshIndicatorState>#1c984]
I/flutter ( 5252): [LabeledGlobalKey<RefreshIndicatorState>#dbe20]
the app works, but after changing tabs a few times, it crashes with this error:
I/flutter ( 5252): ══╡ EXCEPTION CAUGHT BY WIDGETS LIBRARY ╞═══════════════════════════════════════════════════════════
I/flutter ( 5252): The following assertion was thrown building NotificationListener<KeepAliveNotification>:
I/flutter ( 5252): Multiple widgets used the same GlobalKey.
I/flutter ( 5252): The key [LabeledGlobalKey<RefreshIndicatorState>#7bd42] was used by multiple widgets. The parents of
I/flutter ( 5252): those widgets were:
I/flutter ( 5252): - RepaintBoundary-[<[LabeledGlobalKey<RefreshIndicatorState>#7bd42]>](renderObject:
I/flutter ( 5252): RenderRepaintBoundary#60a4a DETACHED)
I/flutter ( 5252): - RepaintBoundary-[<[LabeledGlobalKey<RefreshIndicatorState>#7bd42]>](renderObject:
I/flutter ( 5252): RenderRepaintBoundary#c8cdb NEEDS-LAYOUT NEEDS-PAINT)
I/flutter ( 5252): A GlobalKey can only be specified on one widget at a time in the widget tree.
The keys are generated in the Build method, so, I don't understand why the Multiple widgets used the same GlobalKey
error
Why the key is generated again, and why it's not unique? I'm not talking of a thousand intents, the error appears after changing between tabs 4 or 5 times.Thank you for any help.
解决方案 Could you create your keys "by hand" and use static/constant values? e.g. ...
import 'package:flutter/widgets.dart';
class RIKeys {
static final riKey1 = const Key('__RIKEY1__');
static final riKey2 = const Key('__RIKEY2__');
static final riKey3 = const Key('__RIKEY3__');
}
then in ...
body: new TabBarView(
children: [
new RefreshIndicator(new RefreshIndicator(
// Use the Manual Static Value instead ...
key: RIKeys.riKey1,
onRefresh: _actualizoData,
child: new ListView.builder(
padding: new EdgeInsets.only(top: 5.0),
itemCount: linea_reservas.length * 2,
itemBuilder: (BuildContext context, int position) {
if (position.isOdd) return new Divider();
final index = position ~/ 2;
return _buildRow(index);
}),
),
I have done this in a similar situation with some success ... especially with redux or other similar patterns ...
这篇关于多个小部件使用相同的GlobalKey的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!