颤振在渲染的小部件中剪切文本的顶部或底部

时间:2020-07-29 09:50:55

标签: android image flutter text widget

为了优化FPS,我决定渲染并显示小部件。我的文字有问题,因为文字被剪掉了,我不知道为什么。下面的示例显示了我的“ RenderedTextWithStroke”的外观和代码。

我在三星S7上进行了测试。当我输入“ Wyzwanie!”字样时在三行中,中线呈现良好。也许问题出在渲染小部件的边缘。我可以增加渲染的小部件的大小吗?

Image with problem

import 'dart:typed_data';

import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart';
import 'package:meloapp/core/utils/logger.dart';
import 'package:meloapp/core/utils/screen_information/sizing_information.dart';
import 'package:meloapp/core/values/styles.dart';
import 'dart:ui' as ui;

class TextWithStrokeRendered extends StatelessWidget {
  final double fontSize;
  final Color strokeColor;
  final Color backgroundColor;
  final String text;
  String font;
  double strokeWidth;
  TextAlign alignment;
  final _globalKey = GlobalKey();
  Widget imageWidget;
  static const _MAX_ATTEMPTS_TO_LOAD_IMAGE = 5;
  int attempts = 0;

  TextWithStrokeRendered({Key key,
    @required this.text,
    @required this.strokeColor,
    @required this.fontSize,
    @required this.backgroundColor,
    this.font,
    this.strokeWidth,
    this.alignment: TextAlign.start})
      : super(key: key) {
    if (strokeWidth == null) {
      strokeWidth = fontSize / 5;
    }
    if (font == null) {
      font = defaultFont;
    }
  }

  @override
  Widget build(BuildContext context) {
    return imageWidget ??
        FutureBuilder<Widget>(
            future: _captureImage(context),
            builder: (context, snapshot) {
              if (snapshot.hasData) {
                return snapshot.data;
              } else {
                return RepaintBoundary(
                    key: _globalKey,
                    child: Material(
                        type: MaterialType.transparency,
                        child: Stack(
                          children: <Widget>[
                            // Stroked text as border.
                            Text(
                              text,
                              style: TextStyle(
                                fontSize: fontSize,
                                fontFamily: font,
                                height: 1.0,
                                foreground: Paint()
                                  ..style = PaintingStyle.stroke
                                  ..strokeWidth = strokeWidth
                                  ..color = strokeColor,
                              ),
                              textAlign: alignment,
                            ),
                            // Solid text as fill.
                            Text(
                              text,
                              style: TextStyle(
                                fontSize: fontSize,
                                fontFamily: font,
                                height: 1.0,
                                color: backgroundColor,
                              ),
                              textAlign: alignment,
                            ),
                          ],
                        )));
              }
            });
  }

  Future<Widget> _captureImage(BuildContext context) async {
    Logger.debug("Start capture image from stroke text $text");
    while (imageWidget == null) {
      try {
        await Future.delayed(Duration(milliseconds: 50));
        attempts++;
        if (attempts >= _MAX_ATTEMPTS_TO_LOAD_IMAGE) break;
        if (_globalKey.currentContext == null) {
          await Future.delayed(Duration(milliseconds: 50));
          if (_globalKey.currentContext == null) continue;
        }
        RenderRepaintBoundary boundary = _globalKey.currentContext.findRenderObject();
        if (boundary.debugNeedsPaint) {
          continue;
        }
        ui.Image image = await boundary.toImage(pixelRatio: SizingInformation.devicePixelRatio ?? 1.0);
        ByteData byteData = await image.toByteData(format: ui.ImageByteFormat.png);
        final pngBytes = byteData.buffer.asUint8List();
        precacheImage(MemoryImage(pngBytes, scale: SizingInformation.devicePixelRatio ?? 1.0), context);
        await Future.delayed(Duration(milliseconds: 20));
        imageWidget = Image.memory(
          pngBytes,
          scale: SizingInformation.devicePixelRatio ?? 1.0,
          fit: BoxFit.scaleDown,
        );
        Logger.debug("Image captured $text");
        return imageWidget;
      } catch (exception) {
        Logger.logError(exception);
      }
    }
  }
}

0 个答案:

没有答案