flutter-quill Rich text editor for Flutter 项目地址: https://gitcode.com/gh_mirrors/fl/flutter-quill
在富文本编辑器的开发中,我们经常需要超越纯文本的限制,嵌入各种自定义内容。Flutter-Quill作为一款强大的富文本编辑器组件,提供了灵活的扩展机制,允许开发者创建自定义嵌入块(Custom Embed Blocks)。本文将深入探讨如何在Flutter-Quill中实现这一功能。
自定义嵌入块是指可以在富文本编辑器中插入的非标准内容单元,它们可以是:
首先需要定义一个继承自CustomBlockEmbed
的类,这个类负责数据的序列化和反序列化:
class NotesBlockEmbed extends CustomBlockEmbed {
const NotesBlockEmbed(String value) : super(noteType, value);
static const String noteType = 'notes';
static NotesBlockEmbed fromDocument(Document document) =>
NotesBlockEmbed(jsonEncode(document.toDelta().toJson()));
Document get document => Document.fromJson(jsonDecode(data));
}
关键点解析:
noteType
是嵌入块的唯一标识符fromDocument
方法将富文本文档转换为可存储的格式document
getter方法实现数据的反向解析接下来需要创建实际的Flutter小部件来展示嵌入内容:
class NotesEmbedBuilder extends EmbedBuilder {
NotesEmbedBuilder({required this.addEditNote});
final Future Function(BuildContext context, {Document? document}) addEditNote;
@override
String get key => 'notes';
@override
Widget build(BuildContext context, EmbedContext embedContext) {
final notes = NotesBlockEmbed(embedContext.node.value.data).document;
return Material(
color: Colors.transparent,
child: ListTile(
title: Text(
notes.toPlainText().replaceAll('\n', ' '),
maxLines: 3,
overflow: TextOverflow.ellipsis,
),
leading: const Icon(Icons.notes),
onTap: () => addEditNote(context, document: notes),
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(10),
side: const BorderSide(color: Colors.grey),
),
),
);
}
}
设计考虑:
ListTile
提供良好的触摸反馈核心交互逻辑处理:
Future _addEditNote(BuildContext context, {Document? document}) async {
final isEditing = document != null;
final controller = QuillController(
document: document ?? Document(),
selection: const TextSelection.collapsed(offset: 0),
);
await showDialog(
context: context,
builder: (context) => AlertDialog(
title: Row(
children: [
Text('${isEditing ? 'Edit' : 'Add'} note'),
IconButton(
onPressed: () => Navigator.of(context).pop(),
icon: const Icon(Icons.close),
)
],
),
content: QuillEditor.basic(
controller: controller,
config: const QuillEditorConfig(),
),
),
);
if (controller.document.isEmpty()) return;
final block = BlockEmbed.custom(
NotesBlockEmbed.fromDocument(controller.document),
);
if (isEditing) {
final offset = getEmbedNode(controller, controller.selection.start).offset;
controller.replaceText(offset, 1, block, TextSelection.collapsed(offset: offset));
} else {
controller.replaceText(controller.selection.start, 0, block, null);
}
}
关键逻辑:
实现后的自定义笔记嵌入块会显示为带有图标的可点击区域,点击后可以编辑富文本内容。在编辑器中,它会以紧凑的形式展示内容预览,保持界面的整洁性。
性能优化:
AutomaticKeepAliveClientMixin
didUpdateWidget
以优化重建性能数据安全:
交互设计:
样式定制:
问题1:嵌入块无法正确渲染
key
值是否与CustomBlockEmbed
的类型标识一致QuillEditor
的embedBuilders
参数问题2:编辑后内容未更新
replaceText
方法问题3:序列化异常
这种自定义嵌入块机制可以衍生出许多高级应用场景:
通过深入理解Flutter-Quill的嵌入块机制,开发者可以突破传统富文本编辑器的限制,创造出真正符合业务需求的编辑体验。
flutter-quill Rich text editor for Flutter 项目地址: https://gitcode.com/gh_mirrors/fl/flutter-quill