目的是為了實(shí)現(xiàn) 高德地圖Marker自定義,坑爹的只支持 本地素材 和 Uint8List,所以只能轉(zhuǎn)換了。
網(wǎng)上搜 Widget 轉(zhuǎn) Image,基本都是需要在 build 內(nèi)部實(shí)現(xiàn),然后賦值一個(gè)key,生成 Uint8List。也就是將已經(jīng)顯示到頁(yè)面上的 Widget 轉(zhuǎn)成圖片。
而地圖的 Marker 需要在加載數(shù)據(jù)庫(kù)時(shí)執(zhí)行,顯然不可行。
直接搜“高德地圖Marker自定義”,還能搜到幾篇文章?;径际峭粋€(gè)答案,代碼如下:
static Future<ByteData> widgetToImage(
Widget widget, {
Alignment alignment = Alignment.center,
Size size = const Size(double.maxFinite, double.maxFinite),
double devicePixelRatio = 1.0,
double pixelRatio = 1.0,
}) async {
RenderRepaintBoundary repaintBoundary = RenderRepaintBoundary();
RenderView renderView = RenderView(
child: RenderPositionedBox(alignment: alignment, child: repaintBoundary),
configuration: ViewConfiguration(
size: size,
devicePixelRatio: devicePixelRatio,
),
view: WidgetsBinding.instance.platformDispatcher.views.first,
);
PipelineOwner pipelineOwner = PipelineOwner();
pipelineOwner.rootNode = renderView;
renderView.prepareInitialFrame();
BuildOwner buildOwner = BuildOwner(focusManager: FocusManager());
RenderObjectToWidgetElement rootElement = RenderObjectToWidgetAdapter(
container: repaintBoundary,
child: widget,
).attachToRenderTree(buildOwner);
buildOwner.buildScope(rootElement);
buildOwner.finalizeTree();
pipelineOwner.flushLayout();
pipelineOwner.flushCompositingBits();
pipelineOwner.flushPaint();
ui.Image image = await repaintBoundary.toImage(pixelRatio: pixelRatio);
ByteData? byteData = await image.toByteData(format: ui.ImageByteFormat.png);
return byteData!;
}
然后直接使用就會(huì)成這樣,樣式根本顯示不出來

最終真是皇天不負(fù)苦心人,找到了坑。
問題點(diǎn)在這里:

調(diào)用的時(shí)候,一定要手動(dòng)給于 Size 大小
var byteData = await MapImageUtil.widgetToImage(widget, size: const Size(300, 400));
return BitmapDescriptor.fromBytes(byteData.buffer.asUint8List());
真的是坑啊