Closed paraslamsong closed 1 day ago
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:
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?
You can use flutter_quill_delta_from_html to initialize the QuillController
from a Delta
.
I will close since this feature is not supported by default in Flutter Quill and it is not a standard of Quill js.
Faced the problem to use html string but the package is not allowing to use html string as input.