设置内容样式包含字体系列、字体大小和颜色的可编辑列表 (<li>)

Styling contentEditable lists (<li>) with font-family, font-size, and color

本文关键字:字体 列表 编辑 li 颜色 包含 样式 系列 设置      更新时间:2023-09-26

我正在寻找一种设置列表样式的方法,以便它们在 contentEditable 元素中进行编辑时使用用户设置的格式。具体来说,我希望能够以与<li>内容其余内容相同的方式设置数字/项目符号的样式。

从我所做的测试来看,浏览器从不直接设置<li>标签的样式(这实际上控制着数字/项目符号的样式(,而是始终放置一个<font>标签(如果StyleWithCSS,则<span>(作为第一个子节点,使用它进行格式化。我已经尝试了一些想法来解决这个问题,但没有成功:

1. 以编程方式将样式应用于<li>

在这里,我尝试侦听"DOMNodeInserted",当<li>标签插入DOM时,我查询了当前的fontNamefontSizeforeColor命令,并将它们作为内联样式应用于<li>

textarea.addEventListener('DOMNodeInserted', function (evt) {
    if (evt.target.nodeName === 'LI') {
        evt.target.style.color = queryCommandValue('foreColor');
        evt.target.style.fontFamily = queryCommandValue('fontName');
        evt.target.style.fontSize = queryCommandValue('fontSize');
    }
}, false);

即使这样做,一旦您开始输入列表项,浏览器也会尝试变得"智能"并从<li>中删除样式,将它们放入<font>(或<span>(标签中。 :(

2. 为要插入到样式表中的样式创建规则

基于上面的尝试,我没有内联编写样式,而是为它们创建了一个规则,为<li>节点提供了一个 ID,然后将规则插入到样式表中。现在规则将控制<li>的样式,我可以使用CSSOM不断更新任何特定<li>的样式。

这似乎工作得很好(有一些错误需要解决(,但是,它完全破坏了内容可编辑的撤消堆栈。由于撤消命令仅绑定到textContent和其他格式设置命令,因此无法"撤消"您在样式表中设置的样式。(至少不是很直观,我已经考虑过如何做到这一点......

3. 注意<li>属性的变化并保留它们

在这次尝试中,我使用了 DOM 级别 4 中新提供的 MutationObserver http://www.w3.org/TR/dom/#mutationobserver。此观察者可以监视节点属性的变化,这些变化将在突变记录中传回。它甚至可以保存以前的属性值,包括style值,因此我可以找出要删除的内容并重新应用它。

var observer = new WebKitMutationObserver(function(mutations) {
    mutations.forEach(function(mutation) {
        if (mutation.target.nodeName === 'LI') {
            ...
        }
    })
});
observer.observe(document, {
    attributes: true,
    subtree: true,
    attributeOldValue: true
});

这仍然缺乏撤消支持。您将撤消其他格式更改,但<li>将保留其样式。

有什么新奇的想法吗?也欢迎仅限现代浏览器的解决方案。我知道我可以格式化自己的 HTML 以用于列表,但我正在尝试查看是否可以使用使用使用实际列表标签的标准insertOrderedListinsertUnorderedList命令来完成此操作。

**

更新 Nov 7 2012 **

看起来还没有人解决这个问题,这里有一个示例 JSFiddle 看看我所描述的内容:http://jsfiddle.net/8LyZR/。只需尝试更改项目符号列表或编号列表的样式即可。

对于我正在从事的项目,我们正在使用我们自己的WebKit构建,因此我们能够通过本机更改来解决此问题,但我希望有一种方法(或将有一种方法(直接使用HTML/CSS/JS执行此操作。

这里有一些有趣的CSS技巧。 http://jsfiddle.net/GZ3cv/

它基本上依赖于在内联标签上放置一个伪元素:before(这将包含样式(,然后尝试将其放置在原始列表项目符号/数字的顶部。

我无法决定是否将其称为解决方案,因为嵌套/内联标签(font,u,b,span,i(的所有不同组合可能会变得不切实际。

但是,只是玩弄字体,大小,颜色和列表类型的控件,似乎可以通过一些明显的彻底调整来模仿您正在寻找的内容。

我很好奇这种技术是合理的还是荒谬的:)就把它扔在那里..