Html 如何将 div 与公共 CSS 样式隔离?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/10064172/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How To Isolate a div from public CSS styles?
提问by Med7at
i have some code for example here in html
我有一些代码,例如在 html 中
<html>
<body>
<img src='an image source'/>
<h1>Hi it's test</h1>
<div id='mydiv'>
<img src='an image source'/>
<h1>Hi it's test</h1>
</div>
</body>
</html>
if i used the following css code for styling it:
如果我使用以下 css 代码对其进行样式设置:
img{
width:100px;
height:100px;
}
h1{
font-size:26px;
color:red;
}
the question is : How can i prevent and isolate the tags inside the mydiv div tag from styling by the public tags style ?
问题是:如何防止和隔离 mydiv div 标签内的标签,使其不受公共标签样式的影响?
回答by jaredjacobs
CSS Cascading and Inheritance Level 3introduces the all
shorthand propertyand the unset
keyword, which, together, allow you to achieve this conveniently.
CSS层叠和继承级别3介绍了all
速记属性和该unset
关键字,这一起,让您方便地实现这一目标。
For example, if an author specifies
all: initial
on an element it will block all inheritance and reset all properties, as if no rules appeared in the author, user, or user-agent levels of the cascade.This can be useful for the root element of a "widget" included in a page, which does not wish to inherit the styles of the outer page. Note, however, that any "default" style applied to that element (such as, e.g.
display: block
from the UA style sheet on block elements such as<div>
) will also be blown away.
例如,如果作者
all: initial
在一个元素上指定,它将阻止所有继承并重置所有属性,就好像没有规则出现在级联的作者、用户或用户代理级别。这对于包含在页面中的“小部件”的根元素非常有用,它不希望继承外部页面的样式。但是请注意,应用于该元素的任何“默认”样式(例如,
display: block
来自块元素上的 UA 样式表,例如<div>
)也将被吹走。
You'll need to apply all: initial
to your div and all: unset
to its descendants:
您需要应用all: initial
到您的 divall: unset
及其后代:
#mydiv {
all: initial; /* blocking inheritance for all properties */
}
#mydiv * {
all: unset; /* allowing inheritance within #mydiv */
}
You may want to use a class on your div instead of an id, so that any rules you write to style its descendants won't have to match or beat the high specificity used in this rule.
您可能希望在您的 div 上使用一个类而不是一个 id,这样您编写的任何规则来设置其后代的样式就不必匹配或击败此规则中使用的高特异性。
To be really safe, you may want to block styles on potential pseudo-element descendants too:
为了真正安全起见,您可能还想阻止潜在伪元素后代的样式:
#mydiv::before,
#mydiv::after,
#mydiv *::before,
#mydiv *::after {
all: unset;
}
Alternatively, for broader browser support, you can manually attempt to do what all
does by setting all known CSS properties (don't forget the prefixed versions):
或者,为了获得更广泛的浏览器支持,您可以手动尝试all
通过设置所有已知的 CSS 属性(不要忘记带前缀的版本)来执行操作:
#mydiv {
/*
* using initial for all properties
* to totally block inheritance
*/
align-content: initial;
align-items: initial;
align-self: initial;
alignment-baseline: initial;
animation: initial;
backface-visibility: initial;
background: initial;
...
}
#mydiv::before,
#mydiv::after,
#mydiv *,
#mydiv *::before,
#mydiv *::after {
/*
* using inherit for normally heritable properties,
* and initial for the others, as unset does
*/
align-content: initial;
align-items: initial;
align-self: initial;
...
color: inherit;
...
}
You can encourage browser support for the all
shorthand property and track its adoption with these issue links:
您可以鼓励浏览器支持all
速记属性并通过以下问题链接跟踪其采用情况:
- ? Chrome37+
- ? Firefox27+
- ? Webkit(Safari 9.1+)
- ? Internet Explorer
- ? Edge
- ? Opera 24+
Up-to-date browser support information for the all
shorthand property is available here.
此处all
提供了有关速记属性的最新浏览器支持信息。
回答by Kamal
You cannot technically, that's how CSS is suppose to work. If there is any style defined for div tag in your style sheet it will be applied to all div elements.
从技术上讲,你不能,这就是 CSS 应该如何工作。如果样式表中为 div 标签定义了任何样式,它将应用于所有 div 元素。
Few things that you can try is don't style with tag nameinstead give class nameand give style declaration to class. so that you can make sure where all styles will go.
您可以尝试的几件事是不要使用标签名称设置样式,而是提供类名并为类提供样式声明。这样您就可以确定所有样式的去向。
OR. if you want some specific Div tag to not have the style while other Divs to have. you can always reset it give some different class name or id and reset the style declarations
或者。如果您希望某些特定的 Div 标签没有样式而其他 Div 有样式。你总是可以重置它给一些不同的类名或 id 并重置样式声明
回答by benface
Old question, but things have changed a little bit since the accepted answer. There is now a CSSWG-recommended keyword called revert
which would be better suited than initial
and unset
to solve this problem, as it resets an element's property to the value defined in the user agent stylesheetrather than the initial value of the property regardless of which element it's used on. So for instance, a div
inside #mydiv
will have its display set to block
as we would expect and not inline
.
老问题,但自接受的答案以来,情况发生了一些变化。现在有一个 CSSWG 推荐的关键字revert
,它更适合initial
并unset
解决这个问题,因为它将元素的属性重置为用户代理样式表中定义的值,而不是属性的初始值,而不管它使用的是哪个元素在。因此,例如,div
内部#mydiv
将其显示设置block
为我们所期望的而不是inline
。
You'd have to do this:
你必须这样做:
#mydiv,
#mydiv::before,
#mydiv::after,
#mydiv *
#mydiv *::before,
#mydiv *::after {
all: revert;
}
Unfortunately, revert
is not supported by any browserother than Safari (for Mac and iOS) at the time of writing.
不幸的是,在撰写本文时,除 Safari(适用于 Mac 和 iOS)之外revert
的任何浏览器都不支持。
There is also something else to take in consideration regarding the accepted answer. If you want to style anything inside #mydiv
, you need to do so with a selector that is at least as specific as the one you used to unset or revert everything, otherwise it will be overridden by that rule, even if it comes after it in the CSS.
关于已接受的答案,还需要考虑其他事项。如果你想在里面设置任何样式#mydiv
,你需要使用一个至少与你用来取消设置或还原所有内容的选择器一样具体的选择器,否则它将被该规则覆盖,即使它出现在它之后CSS。
So you'd need to do something like this (note the #mydiv
which boost the specificityof the rules):
所以你需要做这样的事情(注意#mydiv
提高规则的特殊性):
#mydiv p {
margin-top: 20px;
}
#mydiv .bg-black {
background-color: black;
}
// etc.
回答by Nitin
iframe is also a decent solution for isolation of styles if it doesn't complicate other business logic. Plus this can be done in pure JavaScript and may work in older browsers too.
如果 iframe 不会使其他业务逻辑复杂化,那么它也是一个不错的样式隔离解决方案。此外,这可以在纯 JavaScript 中完成,也可以在旧浏览器中工作。
const HTMLToIsolate = `...` // get your div tag as HTML string
const parentContainerRef = document.body; // or something else
const newIframe = document.createElement('iframe');
// set height & width to 100% and remove borders for newIframe
parentContainerRef.appendChild(newIframe)
newIframe.contentWindow.document.open('text/html', 'replace');
newIframe.contentWindow.document.write(HTMLToIsolate);
newIframe.contentWindow.document.close();
// bonus to remove scroll bars by setting proper iframe's height
newIframe.addEventListener('load', function onIFrameLoad(e) {
const iframeBody = this.contentDocument.querySelector("body");
this.style.height = `${iframeBody.scrollHeight}px`;
});
This worked perfectly for me when I had to embed a complex HTML file into my webpage fetched remotely without MixedContentwarning and without parent HTML styles overriding the embedded HTML. Thanks to https://benfrain.com/sandbox-local-htmlcss-code-snippets-inside-iframe-style-guidespattern-libraries/for this excellent idea!
当我不得不将复杂的 HTML 文件嵌入到远程获取的网页中时,这对我来说非常有效,而没有MixedContent警告,也没有父 HTML 样式覆盖嵌入的 HTML。感谢https://benfrain.com/sandbox-local-htmlcss-code-snippets-inside-iframe-style-guidespattern-libraries/这个绝妙的主意!
Though #mydiv * { all: unset }
CSS trick, as suggested in the accepted solution hereworks, it ended being a complex browser operation as there were many DOM nodes on my page.
尽管#mydiv * { all: unset }
CSS 技巧,正如这里接受的解决方案所建议的那样有效,但它最终成为一个复杂的浏览器操作,因为我的页面上有许多 DOM 节点。
回答by jpsimons
One thing that might be helpful is the CSS direct child selector, which is available in all browsers including IE7+. That lets you apply styling that doesn't cascade down into children. For example in your code you could use this CSS:
可能有用的一件事是CSS 直接子选择器,它在包括 IE7+ 在内的所有浏览器中都可用。这使您可以应用不会向下级联到子项的样式。例如,在您的代码中,您可以使用此 CSS:
body > img {
width:100px;
height:100px;
}
body > h1 {
font-size:26px;
color:red;
}
And that CSS would only apply to elements directly on the BODY element.
并且该 CSS 仅适用于直接在 BODY 元素上的元素。