flutter-quill
flutter-quill copied to clipboard
[Request] Please add raw html string to initialize at controller
Faced the problem to use html string but the package is not allowing to use html string as input.
For now the solution is
_controller.document = quill.Document.fromJson(
jsonDecode(markdownToDelta(html2md.convert(htmlString))),
);
With the use of other packages, html2md and delta_markdown
The problem with converting HTML to Markdown is that we lose all the following properties:
- Background Color
- Color
- Font
- Size
- Strikethrough
- Superscript/Subscript
- Underline
- Text Alignment
- Text Direction
- Formula
- Video
You can write your own converter from HTML to Delta. It works for me
The problem with converting HTML to Markdown is that we lose all the following properties:
- Background Color
- Color
- Font
- Size
- Strikethrough
- Superscript/Subscript
- Underline
- Text Alignment
- Text Direction
- Formula
- Video
You can use my html to Delta converter i wrote.
class HtmlToDeltaConverter {
static const _COLOR_PATTERN = r'color: rgb\((\d+), (\d+), (\d+)\);';
static quill.Delta _parseInlineStyles(htmlDom.Element element) {
var delta = quill.Delta();
for (final node in element.nodes) {
final attributes = _parseElementStyles(element);
if (node is htmlDom.Text) {
delta.insert(node.text, attributes);
}else if (node is htmlDom.Element && node.localName == 'img') {
final src = node.attributes['src'];
if (src != null) {
delta..insert({'image': src});
}
} else if (node is htmlDom.Element) {
delta = delta.concat(_parseInlineStyles(node));
}
}
return delta;
}
static Map<String, dynamic> _parseElementStyles(htmlDom.Element element) {
Map<String, dynamic> attributes = {};
if (element.localName == 'strong') attributes['bold'] = true;
if (element.localName == 'em') attributes['italic'] = true;
if (element.localName == 'u') attributes['underline'] = true;
if (element.localName == 'del') attributes['strike'] = true;
final style = element.attributes['style'];
if (style != null) {
final colorValue = _parseColorFromStyle(style);
if (colorValue != null) attributes['color'] = colorValue;
final bgColorValue = _parseBackgroundColorFromStyle(style);
if (bgColorValue != null) attributes['background'] = bgColorValue;
}
return attributes;
}
static String? _parseColorFromStyle(String style) {
if (RegExp(r'(^|\s)color:(\s|$)').hasMatch(style)) {
return _parseRgbColorFromMatch(RegExp(_COLOR_PATTERN).firstMatch(style));
}
return null;
}
static String? _parseBackgroundColorFromStyle(String style) {
if (RegExp(r'(^|\s)background-color:(\s|$)').hasMatch(style)) {
return _parseRgbColorFromMatch(RegExp(_COLOR_PATTERN).firstMatch(style));
}
return null;
}
static String? _parseRgbColorFromMatch(RegExpMatch? colorMatch) {
if (colorMatch != null) {
try {
final red = int.parse(colorMatch.group(1)!);
final green = int.parse(colorMatch.group(2)!);
final blue = int.parse(colorMatch.group(3)!);
return '#${red.toRadixString(16).padLeft(2, '0')}${green.toRadixString(16).padLeft(2, '0')}${blue.toRadixString(16).padLeft(2, '0')}';
} catch (e) {
debugPrintStack(label: e.toString());
}
}
return null;
}
static quill.Delta htmlToDelta(String html) {
final document = htmlParse.parse(html);
var delta = quill.Delta();
for (final node in document.body?.nodes ?? []) {
if (node is htmlDom.Element) {
switch (node.localName) {
case 'p':
delta = delta.concat(_parseInlineStyles(node))..insert('\n');
break;
case 'br':
delta..insert('\n');
break;
}
}
}
return html.isNotEmpty ? delta : quill.Delta()..insert('\n');
}
}
Using the сonverter:
@override
void initState() {
var delta = HtmlToDeltaConverter.htmlToDelta(widget.htmlString);
_controller = quill.QuillController(
document: quill.Document.fromDelta(delta),
selection: TextSelection.collapsed(offset: 0),
);
super.initState();
}
I tried your converter with the following html:
<div class="Section0">
<p style="text-align:left;page-break-inside:auto;page-break-after:auto;page-break-before:avoid;line-height:normal;margin-top:0pt;margin-bottom:0pt;margin-left:0pt;text-indent:0pt;margin-right:0pt;border-top-style:hidden;border-left-style:hidden;border-right-style:hidden;border-bottom-style:hidden;">
<span lang="en-US" style="font-family:Arial;font-size: 16px;text-transform:none;font-weight:normal;font-style:normal;font-variant:normal;text-decoration: none;">Some text</span>
</p>
</div>
And it didn't work. Also which packages are you using for htmlDom and htmlParser? I used the following:
import 'package:html/parser.dart' as htmlParse;
import 'package:html/dom.dart' as htmlDom;
Thank you for the report, we will take a look at this soon.
Reopened because the converter is experimental and not perfect at all and it used only for pasting contents from external websites
将HTML转换为Markdown的问题是,我们丢失了以下所有属性:
- 背景颜色
- 颜色
- 字体
- 尺寸
- 罢工
- 上标/下标
- 下划线
- 文本对齐
- 文本方向
- 公式
- 视频
Has this problem been solved? How was it solved?