如何在Flutter中截取大于屏幕尺寸的小部件

问题描述 投票:0回答:2

我必须屏幕一个巨大的小部件,他不适合屏幕尺寸,所以我使用了InteractiveView。 该小部件是 graphview 包的图形。

问题是,我必须截图这个小部件。

我使用了 RepaintBoundary 小部件和 Screenshot pub 包,但我有同样的问题, 我只能截屏小部件在屏幕上的部分,而不是屏幕外的部分。

如何截取整个小部件的屏幕截图?

我的代码:

Scaffold(
          body: state.graphInfo.isNotEmpty
              ? RepaintBoundary(
                  key: screen,
                  child: InteractiveViewer(
                    constrained: false,
                    boundaryMargin: const EdgeInsets.all(100),
                    minScale: 0.01,
                    maxScale: 4,
                    child: Column(
                      children: [
                        SizedBox(
                          width: newList.length.toDouble() * 160 + 200,
                          height: 150,
                          child: Container(
                            alignment: Alignment.center,
                            child: ListView.separated(
                              shrinkWrap: true,
                              scrollDirection: Axis.horizontal,
                              separatorBuilder:
                                  (BuildContext context, int index) {
                                return const SizedBox(
                                  width: 40,
                                );
                              },
                              itemCount: newList.length,
                              physics: const NeverScrollableScrollPhysics(),
                              itemBuilder: (context, index) {
                                return SizedBox(
                                  height: 300,
                                  width: 150,
                                  child: Center(
                                    child: Padding(
                                      padding: const EdgeInsets.only(
                                          right: 8.0, left: 8.0),
                                      child: Text(
                                        newList[index],
                                        overflow: TextOverflow.clip,
                                        textAlign: TextAlign.center,
                                      ),
                                    ),
                                  ),
                                );
                              },
                            ),
                          ),
                        ),
                        GraphView(
                          graph: GetGraph.getGraph(state.graphInfo,
                              state.checkList, state.totalPatient),
                          algorithm: BuchheimWalkerAlgorithm(
                              builder, TreeEdgeRenderer(builder)),
                          builder: (Node node) {
                            var a = node.key!.value["label"].round();
                            return circleWidget(a, state.totalPatient);
                          },
                        ),
                      ],
                    ),
                  ),
                )
              : const Center(
                  child: Text("Aucune donnée."),
                ),
          floatingActionButton: state.graphInfo.isNotEmpty
              ? FloatingActionButton(
                  child: const Icon(Icons.screenshot_monitor),
                  onPressed: () async {
                    RenderRepaintBoundary boundary = screen.currentContext!
                        .findRenderObject() as RenderRepaintBoundary;
                    ui.Image image = await boundary.toImage();
                    final byteData =
                        await image.toByteData(format: ui.ImageByteFormat.png);

                    final file = File("${state.output_file}/aller.png");
                    await file.writeAsBytes(byteData!.buffer.asUint8List());
                  },
                )
              : null,
        );
flutter dart widget screenshot
2个回答
0
投票

尝试以某种方式减小小部件的大小,以适合屏幕,然后在生成图像数据时可以使用

pixelRatio
进行放大。

ui.Image image = await boundary.toImage(pixelRatio: 2.5);

0
投票

使用image_gallery_saver。 创建一个 ScreenshotController 并使用该控制器从您希望的任何小部件中捕获。

  class QuotePage extends StatefulWidget {
  var index;

  QuotePage({Key? key, required this.index}) : super(key: key);

  @override
  State<QuotePage> createState() => _QuotePageState();
}

class _QuotePageState extends State<QuotePage> {
  final controller = ScreenshotController();

  @override
  Widget build(BuildContext context) {
    const color = Color(0xFFDFBBB1);

    return Scaffold(
      body: mywidget(),
      floatingActionButton: Padding(
        padding: const EdgeInsets.only(bottom: 20, left: 20),
        child: Row(mainAxisAlignment: MainAxisAlignment.spaceEvenly, children: [
          FloatingActionButton(
            backgroundColor: color,
            heroTag: "btn1",
            child: Icon(
              Icons.copy,
              color: Color.fromARGB(255, 255, 17, 0),
            ),
            onPressed: () {
              FlutterClipboard.copy(copy);
              final snackbar = SnackBar(
                  duration: Duration(seconds: 2),
                  content: const Text(
                    "Quote Copied!",
                    style: TextStyle(
                        fontFamily: "Articulat CF",
                        fontSize: 20,
                        fontStyle: FontStyle.italic),
                  ));
              ScaffoldMessenger.of(context).showSnackBar(snackbar);
            },
          ),
          FloatingActionButton(
            backgroundColor: color,
            heroTag: "btn2",
            child: Icon(
              Icons.download,
              color: Color.fromARGB(255, 255, 17, 0),
            ),
            **onPressed: () async {
              EasyLoading.show(status: "Downloading.....");
              final image = await controller.captureFromWidget(mywidget());
              if (image == null) {
                return;
              } else {
                await saveImage(image);
                EasyLoading.showSuccess('Done!');
                EasyLoading.dismiss();
                
              }**
            },
          ),
          FloatingActionButton(
            backgroundColor: color,
            heroTag: "btn3",
            child: Icon(
              Icons.share,
              color: Color.fromARGB(255, 255, 17, 0),
            ),
            onPressed: () async {
              EasyLoading.show(status: "Just a Sec!");
              final image = await controller.captureFromWidget(mywidget());
              saveAndShare(image);
              EasyLoading.showSuccess("Done!");
              EasyLoading.dismiss();
            },
          )
        ]),
      ),
    );
  }

  saveImage(Uint8List image) async {
    await Permission.storage.request();

    final time = DateTime.now();
    final name = 'download$time';
    final result = await ImageGallerySaver.saveImage(image, name: name);
    return result['filePath'];
  }

  Future saveAndShare(Uint8List bytes) async {
    final directory = await getApplicationDocumentsDirectory();
    final image = File('${directory.path}/download.png');
    image.writeAsBytesSync(bytes);
    final text = "Best App For Fitness and Gym Motivation! Download Now!!";
    await Share.shareFiles([image.path], text: text);
  }

  mywidget() {
    const color = Color(0xFFDFBBB1);

    final db = FirebaseFirestore.instance
        .collection('motivationquotes')
        .orderBy('time', descending: true)
        .snapshots();

    return StreamBuilder<QuerySnapshot>(
      stream: db,
      builder: (context, snapshot) {
        final docs = snapshot.data?.docs;
        if (snapshot.data == null) {
          return const CircularProgressIndicator();
        } else if (snapshot.connectionState == ConnectionState.waiting) {
          return CircularProgressIndicator();
        } else {
          final quote = snapshot.data!.docs[widget.index]['quote'];
          return Column(
            mainAxisAlignment: MainAxisAlignment.center,
            children: [
              Stack(children: [
                Container(
                  width: 500,
                  height: 500,
                  child: Image.network(
                    snapshot.data!.docs[widget.index]['insideImage'],
                    color: Colors.white.withOpacity(0.8),
                    fit: BoxFit.cover,
                    colorBlendMode: BlendMode.modulate,
                  ),
                ),
                Positioned.fill(
                    child: Align(
                        alignment: Alignment.bottomLeft,
                        child: Container(
                          color: Colors.white.withOpacity(0.5),
                          child: Padding(
                            padding: const EdgeInsets.all(8.0),
                            child: Text(
                              copy = quote.toString().toUpperCase(),
                              // textAlign: TextAlign.center,
                              style: TextStyle(
                                  fontSize: 25,
                                  fontWeight: FontWeight.bold,
                                  fontFamily: "Articulat CF",
                                  color: Colors.black),
                            ),
                          ),
                        ))),
              ]),
            ],
          );
        }
      },
    );
  }
}

在这里,在浮动操作按钮 2 的按下功能中,我借助控制器和 captureFromWidget 函数捕获了“我的小部件”。您可以添加您的小部件而不是“我的小部件”并对其进行屏幕截图。

© www.soinside.com 2019 - 2024. All rights reserved.