Flutter:在setState不显示更改后立即将小部件转换为图像
Flutter: converting widget to image just after setState does not show changes
我已经为一个问题苦苦挣扎了几天,我开始怀疑它是否有一个像样的解决方案。
我有一个 Google 地图,我想在其中显示不同的自定义标记,每个标记都是使用来自 API 调用的信息创建的。
为了实现这一点,我使用了一个 Stack 小部件,它有一个位于 Google 地图下方的 RepaintBoundary,因此它是隐藏的。这个 RepaintBoundary 有一个图像和一个文本标签。
Widget build(BuildContext context) {
return new Scaffold(
body: Stack(
children: [
RepaintBoundary(
key: iconKey,
child:
Stack(
children: [
markerIconButton,
markerText,
]
),
),
GoogleMap(
mapType: MapType.normal,
myLocationEnabled: true,
myLocationButtonEnabled:true,
onMapCreated: _onMapCreated,
markers: Set<Marker>.of(_markers),
),
]
),
),
}
当我想放置标记时,我循环遍历 API 调用的结果,并且在每次迭代中,我尝试更改 RepaintBoundary 的图像和文本,将其转换为图像,然后赋值给新的标记,我用的这段代码:
...
for (dynamic result in results) {
...
markerText = result["text"];
backgroundImage = result["assets_image_path"];
setState((){
markerIconButton = new Image.asset(backgroundImage);
markerText = new Text(markerText);
});
// Convert the widget to image
BitmapDescriptor testIcon = await getCustomIcon(iconKey);
Marker marker = Marker(
markerId: MarkerId(index.toString()),
position: LatLng(
result["latitude"],
result["longitude"]
),
icon: testIcon,
);
setState((){
_markers.add(marker);
});
index++;
}
问题是当我调用使用RenderRepaintBoundary.toImage方法的“getCustomIcon”时,新的文本和图像还没有被渲染,所以作为图标传递给当前迭代标记的图像通常属于上一次迭代。有没有办法 运行 将小部件转换为图像的代码确保图像和文本中的更改已呈现?
我尝试首先生成循环中的所有图像并使用 WidgetsBinding.instance.addPostFrameCallback 将它们保存在列表中,但是当我从循环中删除用于添加每个标记的代码时,会跳过很多帧并且只渲染最后一次迭代的图像和文本。
提前致谢。
在转换为图像之前,您没有时间让框架构建您的 UI。 setState 是异步的,并在框架有时间执行时执行。尝试添加延迟:
setState((){
markerIconButton = new Image.asset(backgroundImage);
markerText = new Text(markerText);
});
Future.delayed(Duration(milliseconds: 2000));
// Convert the widget to image
BitmapDescriptor testIcon = await getCustomIcon(iconKey);
我已经为一个问题苦苦挣扎了几天,我开始怀疑它是否有一个像样的解决方案。
我有一个 Google 地图,我想在其中显示不同的自定义标记,每个标记都是使用来自 API 调用的信息创建的。
为了实现这一点,我使用了一个 Stack 小部件,它有一个位于 Google 地图下方的 RepaintBoundary,因此它是隐藏的。这个 RepaintBoundary 有一个图像和一个文本标签。
Widget build(BuildContext context) {
return new Scaffold(
body: Stack(
children: [
RepaintBoundary(
key: iconKey,
child:
Stack(
children: [
markerIconButton,
markerText,
]
),
),
GoogleMap(
mapType: MapType.normal,
myLocationEnabled: true,
myLocationButtonEnabled:true,
onMapCreated: _onMapCreated,
markers: Set<Marker>.of(_markers),
),
]
),
),
}
当我想放置标记时,我循环遍历 API 调用的结果,并且在每次迭代中,我尝试更改 RepaintBoundary 的图像和文本,将其转换为图像,然后赋值给新的标记,我用的这段代码:
...
for (dynamic result in results) {
...
markerText = result["text"];
backgroundImage = result["assets_image_path"];
setState((){
markerIconButton = new Image.asset(backgroundImage);
markerText = new Text(markerText);
});
// Convert the widget to image
BitmapDescriptor testIcon = await getCustomIcon(iconKey);
Marker marker = Marker(
markerId: MarkerId(index.toString()),
position: LatLng(
result["latitude"],
result["longitude"]
),
icon: testIcon,
);
setState((){
_markers.add(marker);
});
index++;
}
问题是当我调用使用RenderRepaintBoundary.toImage方法的“getCustomIcon”时,新的文本和图像还没有被渲染,所以作为图标传递给当前迭代标记的图像通常属于上一次迭代。有没有办法 运行 将小部件转换为图像的代码确保图像和文本中的更改已呈现?
我尝试首先生成循环中的所有图像并使用 WidgetsBinding.instance.addPostFrameCallback 将它们保存在列表中,但是当我从循环中删除用于添加每个标记的代码时,会跳过很多帧并且只渲染最后一次迭代的图像和文本。
提前致谢。
在转换为图像之前,您没有时间让框架构建您的 UI。 setState 是异步的,并在框架有时间执行时执行。尝试添加延迟:
setState((){
markerIconButton = new Image.asset(backgroundImage);
markerText = new Text(markerText);
});
Future.delayed(Duration(milliseconds: 2000));
// Convert the widget to image
BitmapDescriptor testIcon = await getCustomIcon(iconKey);