使用JavaScript在head标签中注入CSS代码动态编辑CSS样式表,这样做好吗?

3

在跨浏览器中注入CSS代码以永久设置/更改某些属性,这是否“合法”且有效?

例如(使用jQuery):

$('head').append('<style>.myclass { background: #f00;}</style>');

我在Safari 7上尝试过,可以使用。

它是否可以跨浏览器使用或是为了避免某些问题而采用的hack?

有没有什么缺点?

3个回答

4
是的,这是合法的 - 而且它比 $(".myclass").css({background: "#FF0"}) 更快,因为您只与 DOM 交互了一次,而不是 N 次(其中 N 是页面上 .myclass 元素的数量)。此外,它将自动应用于未来的 .myclass 元素。
缺点是您可能会遇到特异性问题,因此必须确保以一种方式设计 CSS,以确保可以使用单个类选择器覆盖背景。 (jQuery 的 css 函数,由于直接设置元素的 style 属性,因此默认具有最高的特异性,因此避免了这个特定的问题)。
例如,如果您在链接的样式中有以下 CSS:
#some-id .myclass { background: #000; }

如果DOM中存在$(".myclass").css这样的代码,则会覆盖背景色,而动态注入样式(只注入.myclass { background: #FF0; })则不会被覆盖。

另一个缺点是在老版本的IE中(<=8),你只能创建31个这样的“动态”样式表。在IE >= 9中,这不是问题。


谢谢Sean。你能否更好地解释一下“特异性问题”(或者举个例子)?因为jQuery直接设置样式属性,它会覆盖CSS中的规定。 - Paolo
@Paolo - 添加了示例。 - Sean Vieira

1
我认为你面临着4种解决方案的情况。虽然这些方案都不是非常优雅或完美,但以下是我的建议:
  1. 将CSS注入到HTML的head部分

    这正是你在问题中提出的建议。这个解决方案很好用,但只适用于一次性修改。如果需要进行许多后续修改,则HTML的head部分可能会变得拥挤。

  2. 您可以使用JavaScript检测DOM对象的插入并使它们保持同步

    这里有一个JSFiddle,可以完全实现此功能: http://jsfiddle.net/ITnok/9FQVa/28/

    此解决方案非常适用于您(和您的用户)需要分散在时间上进行多次更改的情况,但前提是您能够控制DOM对象的插入:关键是创建自定义事件以每次插入新对象时触发。

    以下是来自JSFiddle的代码块,用于处理自定义事件:

    //    This event is the key to keep CSS in sync... in realtime!
    $( document )
        .on( 'mickeymouseadded', '.mickeymouse', function( e ) {
            $( this )
                .attr(
                    'style',
                    $( this )
                        .siblings( ':first' )
                        .attr( 'style' )
                );
        } );
    
  3. 您可以使用MutationObserver(旧版且已弃用的Mutation Events的新版本)

    这里是文档链接: https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver

    这是解决问题的绝佳方法,但不幸的是它与旧版Interdict Exploder不兼容(翻译者注:该单词为恶意讽刺IE浏览器)。只有IE11支持它们。

    即使对象插入不在您的直接控制之下,您也可以使用此方法,您无法创建自定义事件或不想这样做。

  4. 您可以使用名为livequery的jQuery插件

    这里是jQuery livequery的Github存储库链接: https://github.com/brandonaaron/livequery

    从未尝试过这个插件,但它看起来可能是一个很好的解决方案,用于查询DOM并确定需要修改和保持同步的内容。

所有这些解决方案都基于Javascript的存在

但根据您告诉我们的情况,我认为这对您不是问题!;-)

希望能帮到您...


-1
如果用户在浏览器中禁用了JavaScript(以加快页面加载速度),那么这可能会成为一个问题。
你应该:
  • 将站点的固定CSS写入CSS文件中
  • 仅在需要解析时使用JS(例如,如果您想要在每个<span class="to_change">...</span>中插入一些CSS)。

2
这不是问题,这是一个JavaScript Web应用程序。如果用户禁用JavaScript,我认为在今天的互联网上将能做很少的事情... - Paolo
OP 特别询问动态编辑 CSS 的方法。如果用户禁用了 JavaScript,则唯一的解决方案是礼貌地请求他们重新启用它。 - hkk
一个网站必须在没有Javascript的情况下清晰易懂。进行CSS修改不是一件好事,只有当您添加页面内容时才需要:比如,如果您的js脚本允许您自定义幻灯片演示文稿,则可以插入幻灯片演示文稿的CSS。你应该在之前就告诉我这是一个javascript webapp。 - Pierre Emmanuel Lallemant

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接