我需要显示长文本,它将占据多个屏幕/页面。我还必须添加一些功能,因此我想实现自己的文本显示组件。
我发现了两个与此任务相对应的类:
TextPainter
将TextSpan用于文本,
将Paint(canvas,offset)用于绘画
段落
使用“队列”来表示文本,而样式
使用Canvas.drawParagraph(paragraph,offset)进行绘画
它们和使用哪个有什么区别?
如果文本包含100行,而页面上只能放置10行,那么如何在下一页上绘制截断的文本,直到没有剩余?
Psy*_*hoX 24
tl;dr:imo TextPainter> Paragraph(因为更好的 API)。
我创建了简单的示例应用程序来比较在(of )上呈现文本的方法TextPainter和Paragraph方法。两种方法都很好,都使用不同的方法,都有奇怪的摆动。CanvasCustomPainter
TextPainter起初我想提一下,TextPainter界面似乎更容易——至少对我来说。您只需要指定text为TextSpanentry 或 tree 并且 - 奇怪的是,它不是默认的 - textDirection。您还可以提供诸如maxLines,style和textAlign(以及其他一些选项)之类的选项。然后您需要使用layout来指定渲染的铺设方式(好吧,maxWidth仅此而已)。最后,paint在某些Canvas指定的Offset。
final TextPainter textPainter = TextPainter(
text: TextSpan(text: text, style: style),
textAlign: TextAlign.justify,
textDirection: TextDirection.ltr
)
..layout(maxWidth: size.width - 12.0 - 12.0);
textPainter.paint(canvas, const Offset(12.0, 36.0));
Run Code Online (Sandbox Code Playgroud)
使用TextSpan在 Flutter 周围非常普遍 -RichText其他小部件也在使用这个类。我还必须注意到,使用TextPainter可以让你检查height和width文本像素的(渲染之前)。
Paragraph第二:Paragraph。这似乎是更底层的、程序化的方法。正如您在下面看到的,Paragraph方法不太干净。首先你必须使用ParagraphBuilder(因为Paragraph没有构造函数)。你需要给它ParagraphStyle一个包含各种文本样式,如字体信息,textAlign,maxLines等等。然后您可以使用pushStyle,pop和addText准备段落的下一部分和下一部分。build获得后Paragraph,您可以drawParagraph在您的Canvas.
final ui.ParagraphBuilder paragraphBuilder = ui.ParagraphBuilder(
ui.ParagraphStyle(
fontSize: style.fontSize,
fontFamily: style.fontFamily,
fontStyle: style.fontStyle,
fontWeight: style.fontWeight,
textAlign: TextAlign.justify,
)
)
..pushStyle(style.getTextStyle())
..addText(text);
final ui.Paragraph paragraph = paragraphBuilder.build()
..layout(ui.ParagraphConstraints(width: size.width - 12.0 - 12.0));
canvas.drawParagraph(paragraph, const Offset(12.0, 36.0));
Run Code Online (Sandbox Code Playgroud)
请注意,有两种类型TextStyle(Dart UI 和 Flutter)。与pushStyle您一致,可以看到Flutter 绘画库已TextStyle转换为Dart UITextStyle。另一个奇怪的事情是你可以/需要在ParagraphBuilder- 即使你要pushStyle在后面的行中使用一些字体设置。并且layout必须用 指定width。
我认为我可以更好地用于读取文件等情况,尤其是在格式化时,因为不需要将文件解析为TextSpan树,这可能会很昂贵。如果您知道自己在做什么,我想它也可以比其他方法快一点,但我没有时间深入挖掘它。
当文本过多时,您可能想要剪切文本。双方Paragraph并TextPainter自曝maxLines-设置最大线-和didExceedMaxLines-检测限是否超出-在这种或那种方式。还有canvas.clipRect相关的方法可以将所有绘图剪辑到选定的空间中。
还有一个简单的性能测试(在发布时),它表明两种方法是可比的(在我的测试案例TextPainter中比 快不超过 2% Paragraph)。也可能是测量误差¯\_(?)_/¯。
| 归档时间: |
|
| 查看次数: |
754 次 |
| 最近记录: |