css hack

判断浏览器内核 CSS3中各个浏览器内核兼容的设置

什么是css内核

浏览器最重要或者说核心的部分是“Rendering Engine”,可大概译为“渲染引擎”,不过我们一般习惯将之称为“浏览器内核”。负责对网页语法的解释(如标准通用标记语言下的一个应用HTML、JavaScript)并渲染(显示)网页。 所以,通常所谓的浏览器内核也就是浏览器所采用的渲染引擎,渲染引擎决定了浏览器如何显示网页的内容以及页面的格式信息。不同的浏览器内核对网页编写语法的解释也有不同,因此同一网页在不同的内核的浏览器里的渲染(显示)效果也可能不同,这也是网页编写者需要在不同内核的浏览器中测试网页显示效果的原因。

一、Trident内核代表产品Internet Explorer,又称其为IE内核。Trident(又称为MSHTML),是微软开发的一种排版引擎。使用Trident渲染引擎的浏览器包括:IE、傲游、世界之窗浏览器、Avant、腾讯TT、Netscape 8、NetCaptor、Sleipnir、GOSURF、GreenBrowser和KKman等。

二、Gecko内核代表作品Mozilla FirefoxGecko是一套开放源代码的、以C++编写的网页排版引擎。Gecko是最流行的排版引擎之一,仅次于Trident。使用它的最著名浏览器有Firefox、Netscape6至9。

三、WebKit内核代表作品Safari、Chromewebkit 是一个开源项目,包含了来自KDE项目和苹果公司的一些组件,主要用于Mac OS系统,它的特点在于源码结构清晰、渲染速度极快。缺点是对网页代码的兼容性不高,导致一些编写不标准的网页无法正常显示。主要代表作品有Safari和Google的浏览器Chrome。

四、Presto内核代表作品OperaPresto是由Opera Software开发的浏览器排版引擎,供Opera 7.0及以上使用。它取代了旧版Opera 4至6版本使用的Elektra排版引擎,包括加入动态功能,例如网页或其部分可随着DOM及Script语法的事件而重新排版。

CSS3中-moz、-ms、-webkit和-o分别代表什么意思

1、-moz-:代表FireFox浏览器私有属性
2、-ms-:代表IE浏览器私有属性
3、-webkit-:代表safari、chrome浏览器私有属性
4、-o-:代表opera浏览器私有属性

浅谈各种浏览器下的CSS Hack兼容性写法

做前端多年,虽然不是经常需要hack,但是我们经常会遇到各浏览器表现不一致的情况。基于此,某些情况我们会极不情愿的使用这个不太友好的方式来达到大家要求的页面表现。我个人是不太推荐使用hack的,要知道一名好的前端,要尽可能不使用hack的情况下实现需求,做到较好的用户体验。可是啊,现实太残酷,浏览器厂商之间历史遗留的问题让我们在目标需求下不得不向hack妥协,虽然这只是个别情况。

由于不同浏览器所遵循的标准也有所不同,再加上不可避免的程序bug、经济利益等因素的干扰。同样的网页代码(HTML + CSS),在不同浏览器上的显示效果却略有不同,甚至大有不同。即使是同一个浏览器,其不同版本的显示效果也有所不同,尤其是IE。这就给网页前端设计人员带来了很大的困扰。开发人员必须兼顾考虑到所有主流的浏览器,才能在不同的浏览器上显示出相同或满足需要的效果。于是CSS Hack技术就诞生了。

浏览器大战
第一次浏览器大战发生在上个世纪90年代,微软发布了它的IE浏览器,和网景公司的Netscape Navigator‘大打出手’,最后网景不得不将公司卖给AOL一走了之。世界由此平静了。但平静并没有能够持续太久,日益壮大的Mozilla Firefox从2004年又开始重新叫板微软地位。
在1995年以前,网景是互联网浏览器的绝对标准,因为虽然它的正式版本要收费,但是评估版是随便下载而且免费的。尽管微软从1995年8月开始发布IE 1.0,但真正惊动市场的是1997年10月份发布的IE 4.0浏览器。这一款浏览器比网景更好的遵循了World Wide Web Consortium (W3C)提出的互联网标准,并能够提供一些诸如MP3播放之类的功能。自此以后,IE破竹之势一发不可收拾,再加上微软巨大的财力、人力后盾,网景终于在1998年以48亿美元的价格出售给了AOL公司。而后,网景被AOL变成了它ISP业务的门面,网景浏览器的核心团队至此已经全部离队。于是,第一回合微软大胜。
然而,事情并没有就此结束。1998年网景公开了它的浏览器源码,并重新命名为Mozilla,全部程序进行了重写。2002年发布了第一个版本。2004年基于Mozilla源码的Firefox首次登台,拉开了第二次浏览器大战的序幕。直到同年2月份,微软的浏览器份额已经从最高点的96%下降到了85%,主要是由于Firefox的强烈市场攻势。于是乎,微软再次全力以赴,迅速提前了原定配合Longhorn Windows版本的IE 7.0的发布日期,用来与火狐狸(Firefox)抗衡。

那么第一次大战带来的后果是什么呢
在大战中,两者在浏览器开发上,为压倒对手,做出了以下两大行为:
1、把加入新功能的重要性放在修正错误之前。
2、使用专属格式,不尊重公开标准。

第二次大战并不像第一次那么简单。这次不只是IE和火狐狸的斗争了。一些新的基于不同引擎的浏览器也加入了阵营,比如挪威的Opera (基于Presto引擎)和中国的Maxthon。目前Opera的主要战场在移动设备,大部分的智能手机都配有Opera的移动浏览器。而Maxthon的主要阵地在中国,根据百度的统计,15%的百度用户都在使用这个浏览器
一直到2006年10月底,Internet Explorer 7及Mozilla Firefox 2相继发行。IE7短短几天内下载量即突破三百万[20],由此可见广大Windows的用户对IE7的关注程度。然而,IE7正式版发行几小时后即发现安全漏,相对市场上众多浏览器,并不新颖的功能,部分剥离Windows系统后造成其资源占用倍增,需要掏腰包才能享受的扩展服务,且不支持较低版本如Windows 2000系统,都让人失望。当然,IE亦有其无可比拟的优势,譬如操作系统捆绑,众多功能丰富的第三方浏览器无法提供而造就的IE网页标准垄断,这是其他浏览器无法企及的。再看Firefox 2.0,对网页标准及新技术的支持,相对安全的浏览体验(虽然漏洞不断,但至今为止尚无因攻击Firefox而造成用户损失的新闻),让其在技术上领先IE浏览器,但相对“复杂”的操作及对“IE网页标准支持不完善”使大部分普通用户望之怯步,其市场占有率一直稳定在16%-18%之间。

中国市场
360安全浏览器、搜狗高速浏览器、QQ浏览器、傲游浏览器为Internet Explorer在中国的主要竞争对手,并且不少中国的浏览器开始使用两个以上的排版引擎。然而中国的浏览器多为IE核心的外壳浏览器,所以称为IE竞争对手,并不准确。
如今随着春运抢票插件的流行以及360极速浏览器(基于Chromium内核)的推出,Internet Explorer在中国的市场份额正在急遽下降。

什么是CSS hack

由于不同厂商的流览器或某浏览器的不同版本(如IE6-IE11,Firefox/Safari/Opera/Chrome等),对CSS的支持、解析不一样,导致在不同浏览器的环境中呈现出不一致的页面展现效果。这时,我们为了获得统一的页面效果,就需要针对不同的浏览器或不同版本写特定的CSS样式,我们把这个针对不同的浏览器/不同版本写相应的CSS code的过程,叫做CSS hack!

CSS hack分类

CSS Hack大致有几种表现形式,CSS属性前缀法、选择器前缀法以及IE条件注释法(即HTML头部引用if IE)Hack,实际项目中CSS Hack大部分是针对IE浏览器不同版本之间的表现差异而引入的。

如果在一个css样式选择器中存在两个名称相同的属性,浏览器一般会以最后面的属性为准。

<style type="text/css">   
.css-hack {   
    background-color: red;   
    background-color: blue; /* 最终背景色显示为蓝色 */  
}   
</style>   
<div class="css-hack">CodePlayer</div>  

当然,这里有个前提,那就是浏览器首先得能够识别并支持该css属性,对于浏览器不支持的css属性或值,浏览器将一律将其忽略。
这就是CSS Hack技术的实现原理。例如:即使我们在属性名称前面加上一个下划线_,IE 6 照样可以识别该属性,而且只有IE 6可以识别。因此,我们就可以利用这个特性,让IE 6实现某些特定的效果。

.css-hack {   
    background-color: red; /* 在其他浏览器上显示为红色 */  
    _background-color: blue; /* 在IE 6上显示为蓝色 */  
}  

再者如,由于IE 6不支持max-width属性,但是IE6的css属性值支持expression表达式。因此,我们可以为IE 6 折中实现max-width的属性效果。

.css-hack {   
    background-color: red;   
    max-width: 200px;   
    _width: expression( function(me){ var maxWidth = 200; me.style.width = (me.offsetWidth <= maxWidth ? me.offsetWidth : maxWidth) + "px"; }(this) ); /* _开头只有IE6可以识别,出于性能考虑,此处的表达式只会执行一次 */  
}  

下面,我们就来探讨IE 6-11、FireFox、Chrome、Safari、Opera等浏览器的CSS Hack技术,以供特定浏览器进行特定属性的识别(国产浏览器一般都使用IE或Chromium内核,因此不予考虑)。

上面说过了 css hack 有几种方法:
属性前缀法(即类内部Hack):例如 IE6能识别下划线”“和星号” * “,IE7能识别星号” * “,但不能识别下划线”“,IE6~IE10都认识”\9”,但firefox前述三个都不能认识。

IE浏览器的CSS Hack

所有的IE浏览器的CSS Hack

由于所有的IE浏览器都能够识别特定的css属性值后缀\9,因此我们可以给css的属性值添加\9后缀(在结尾的分号之前),从而做到只有IE浏览器能够识别该属性,其他浏览器无法识别从而将其忽略掉。

.css-hack {   
    background-color: red; /* 其他浏览器上显示为红色 */  
    background-color: blue \9; /* 所有IE浏览器上显示为蓝色 */  
}  

IE 6的CSS Hack

毫无疑问,如上所述,为css的属性前面加下划线_,这是给IE6专用的。

.css-hack {   
    background-color: red; /* 其他浏览器上显示为红色 */  
    _background-color: blue; /* 只有IE 6浏览器上显示为蓝色 */  
}  

IE 7的CSS Hack

IE7能够识别加了前缀的css属性名称,但是IE 7不支持_前缀,而IE6支持。因此,我们可以先写一个属性让IE6、IE7都能识别,再写一个_属性,只让IE6识别,将属性值复原回去,从而让前者只对IE 7生效。

.css-hack {   
    color: red; /* 其他浏览器上显示为红色 */  
     _color: red; /* 让 IE 6 复原为之前设置的颜色 */  
}  

注意:有些网页上说,只用+、或者#号的属性前缀就可以只让IE 7进行单独识别。不过经过本人亲测,不管是用IE Tester,还是专门下载一个XP系统,用原版IE 6测试,都表明:IE6、IE7共同只可以识别的属性前缀。
另外,还有人说,IE 7支持!important,IE 6不支持!important,因此可以通过*属性: 值!important;的形式来实现IE 7的CSS Hack。
实际上,这样也是不行的,因为IE 6不是不支持!important,只是有个bug而已,详情请参见IE6究竟支不支持!important和IE6 IE7(Q) IE8(Q) 不完全支持!important规则。
使用!important来实现IE 7的CSS Hack,必须是在同一个样式选择器中,而且同样需要在后面加_属性来复原IE 6的设置(这种方式还麻烦点,上面的方法还少写个!important)。

.css-hack {   
    color: red; /* 其他浏览器上显示为红色 */  
    *color: blue !important; /* 只有 IE 6、IE 7 浏览器上显示为蓝色 */  
    _color: red; /* 让 IE 6 复原为之前设置的颜色 */  
}  

慎用\0的CSS Hack

网上许多与CSS Hack相关的文章中说,在css的属性值和分号之间添加字符\0,可以实现对IE 8或 IE 9的CSS hack(有的说,仅支持IE8)。
网上的示例是这样的:

.css-hack {   
    color: red; /* 其他浏览器显示红色 */  
    color: blue\0; /* IE8、IE9 显示蓝色 */  
    *color: green; /* IE7 显示绿色 */  
    _color: brown; /* IE6 显示棕色 */  
}  

通过实际测试发现,关于使用字符\0实现的上述CSS Hack有2点需要注意。
1、IE10和IE11(edge)也能够识别添加了字符\0的css属性值2、属性值和\0之间不能有空格,有一个空格的话(例如:blue \0),在IE 7 IE9 IE10中就失效了,仅对IE 5/IE 8有效。

.css-hack {   
    color: red; /* 其他浏览器显示红色 */  
    color: blue\0; /* IE8~IE911显示蓝色 */  
}  

这个时候,在IE 6、IE 7浏览器中,你会发现你看到的 文字不是红色,而是黑色(也就是默认的字体颜色)!
这是因为一般浏览器的思路是,先过滤掉无效的css属性值,然后再从正确的属性设置中根据优先级获取最后面的css属性值。而IE 6/7浏览器不是先过滤掉无效的属性值,而是先根据优先级,获取最后面的css属性值,然后再来判断该属性值是否,无效就忽略掉。因此,如果按照网上所说,仅仅使用\0来实现IE 8+的CSS Hack,则会对IE6/7中的显示效果造成破坏。你必须通过额外的css属性设置来复原IE6/7的样式。
因为,我们不能够简单地下结论说,使用\0可以实现对IE 8、IE 9甚至IE 10 +的CSS Hack。

IE条件注释法(即HTML条件注释Hack):针对所有IE(注:IE10+已经不再支持条件注释): ,针对IE6及以下版本: 。这类Hack不仅对CSS生效,对写在判断语句里面的所有代码都会生效。

CSS hack书写顺序,一般是将适用范围广、被识别能力强的CSS定义在前面。

CSS hack方式一:条件注释法
 
这种方式是IE浏览器专有的Hack方式,微软官方推荐使用的hack方式。举例如下

只在IE下生效

只在IE6下生效

只在IE6以上版本生效

只在IE8上不生效

CSS hack方式二:内属性前缀法
属性前缀法是在CSS样式属性名前加上一些只有特定浏览器才能识别的hack前缀,以达到预期的页面展现效果。

IE浏览器各版本 CSS hack 对照表
hack 写法 实例 IE6(S) IE6(Q) IE7(S) IE7(Q) IE8(S) IE8(Q) IE9(S) IE9(Q) IE10(S) IE10(Q)
* *color 青色 Y Y Y Y N Y N Y N Y
+ +color 绿色 Y Y Y Y N Y N Y N Y
- -color 黄色 Y Y N N N N N N N N
_ _color 蓝色 Y Y N Y N Y N Y N N
#color 紫色 Y Y Y Y N Y N Y N Y
\0 color:red\0 红色 N N N N Y N Y N Y N
\9\0 color:red\9\0 粉色 N N N N N N Y N Y N
!important color:blue !important;color:green; 棕色 N N Y N Y N Y N Y Y

说明:在标准模式中

“-″减号是IE6专有的hack
“\9″ IE6/IE7/IE8/IE9/IE10都生效
“\0″ IE8/IE9/IE10都生效,是IE8/9/10的hack
“\9\0″ 只对IE5/IE6/IE8/IE9/IE10生效,是IE5/IE6/IE8/IE9/10的hack


body:nth-of-type(1) .iehack{
color: #F00;/* 对Windows IE9/Firefox 7+/Opera 10+/所有Chrome/Safari的CSS hack ,选择器也适用几乎全部Mobile/Linux/Mac browser*/
}
.demo1,.demo2,.demo3,.demo4{
width:100px;
height:100px;
}
.hack{
/demo1 /
/demo1 注意顺序,否则IE6/7下可能无法正确显示,导致结果显示为白色背景/
background-color:red; /* All browsers */
background-color:blue !important;/* All browsers but IE6 */
background-color:black; / IE6, IE7 */
background-color:gray\9; /* IE6, IE7, IE8, IE9, IE10 */
background-color:purple\0; /* IE8, IE9, IE10 */
background-color:orange\9\0;/IE9, IE10/
_background-color:green; /* Only works in IE6 */
+background-color:pink; / WARNING: Only works in IE7 ? Is it right? */
}

/可以通过javascript检测IE10,然后给IE10的标签加上class=”ie10″ 这个类 /
.ie10 #hack{
color:red; /* Only works in IE10 */
}

/demo2/
.iehack{
/*该demo实例是用于区分标准模式下ie6~ie9和Firefox/Chrome的hack,注意顺序
IE6显示为:绿色,
IE7显示为:黑色,
IE8显示为:红色,
IE9显示为:蓝色,
Firefox/Chrome显示为:橘色,
(本例IE10效果同IE9,Opera最新版效果同IE8)
*/
background-color:orange; /* all - for Firefox/Chrome */
background-color:red\0; /* ie 8/9/10/Opera - for ie8/ie10/Opera */
background-color:blue\9\0; /* ie 9/10 - for ie9/10 */
background-color:black; / ie 6/7 - for ie7 */
_background-color:green; /* ie 6 - for ie6 */
}

/*demo3
实例是用于区分标准模式下ie6~ie9和Firefox/Chrome的hack,注意顺序
IE6显示为:红色,
IE7显示为:蓝色,
IE8显示为:绿色,
IE9显示为:粉色,
Firefox/Chrome显示为:橘色,
(本例IE10效果同IE9,Opera最新版效果也同IE9为粉色)

*/
.element {
background-color:orange; /* all IE/FF/CH/OP*/
}
.element {
background-color: blue; / IE6+7, doesn’t work in IE8/9 as IE7 */
}
.element {
_background-color: red; /* IE6 */
}
.element {
background-color: green\0; /* IE8+9+10 */
}
:root .element { background-color:pink\0; } /* IE9+10 */

/demo4/
/*

该实例是用于区分标准模式下ie6~ie10和Opera/Firefox/Chrome的hack,本例特别要注意顺序
IE6显示为:橘色,
IE7显示为:粉色,
IE8显示为:黄色,
IE9显示为:紫色,
IE10显示为:绿色,
Firefox显示为:蓝色,
Opera显示为:黑色,
Safari/Chrome显示为:灰色,

*/
.hacktest{
background-color:blue; /* 都识别,此处针对firefox */
background-color:red\9; /all ie/
background-color:yellow\0; /for IE8/IE9/10 最新版opera也认识/
_background-color:orange; /for ie6/
}

@media screen and (min-width:0){
.hacktest {background-color:black\0;} /opera/
}
@media screen and (min-width:0) {
.hacktest { background-color:purple\9; }/* for IE9/IE10 PS:国外有些习惯常写作\0,根本没考虑Opera也认识\0的实际 */
}
@media screen and (-ms-high-contrast: active), (-ms-high-contrast: none) {
.hacktest { background-color:green; } /* for IE10+ 此写法可以适配到高对比度和默认模式,故可覆盖所有ie10的模式 */
}
@media screen and (-webkit-min-device-pixel-ratio:0){ .hacktest {background-color:gray;} } /for Chrome/Safari/

/* #963棕色 :root is for IE9/IE10, 优先级高于@media, 慎用!如果二者合用,必要时在@media样式加入 !important 才能区分IE9和IE10 */
/*
:root .hacktest { background-color:#963\9; }
*/

demo1是测试不同IE浏览器下hack 的显示效果
IE6显示为:粉色,
IE7显示为:粉色,
IE8显示为:蓝色,
IE9显示为:蓝色,
Firefox/Chrome/Opera显示为:蓝色,
若去掉其中的!important属性定义,则IE6/7仍然是粉色,IE8是紫色,IE9/10为橙色,Firefox/Chrome变为红色,Opera是紫色。是不是有些奇怪:除了IE6以外,其他所有的表现都符合我们的期待。那为何IE6表现的颜色不是_background-color:green;的绿色而是+background-color:pink的粉色呢?其实是最后一句所谓的IE7私有hack惹的祸?不是说+是IE7的专有hack吗???错,你可能太粗心了!我们常说的IE7专有+hack的格式是+html selector,而不是上面的直接在属性上加*+前缀。如果是为IE7定制特殊样式,应该这样使用:

+html #ie7test { / IE7 only*/
color:green;
}
经过测试,我发现属性前缀+background-color:pink;只有IE6和IE7认识。而+html selector只有IE7认识。所以我们在使用时候一定要特别注意。

demo2实例是用于区分标准模式下ie6~ie9和Firefox/Chrome的hack,注意顺序
IE6显示为:绿色,
IE7显示为:黑色,
IE8显示为:红色,
IE9显示为:蓝色,
Firefox/Chrome显示为:橘色,
(本例IE10效果同IE9,Opera最新版效果同IE8)

demo3实例也是用于区分标准模式下ie6~ie9和Firefox/Chrome的hack,注意顺序
IE6显示为:红色,
IE7显示为:蓝色,
IE8显示为:绿色,
IE9显示为:粉色,
Firefox/Chrome显示为:橘色,
(本例IE10效果同IE9,Opera最新版效果也同IE9为粉色)

demo4实例是用于区分标准模式下ie6~ie10和Opera/Firefox/Chrome的hack,本例特别要注意顺序
IE6显示为:橘色,
IE7显示为:粉色,
IE8显示为:黄色,
IE9显示为:紫色,
IE10显示为:绿色,
Firefox显示为:蓝色,
Opera显示为:黑色,
Safari/Chrome显示为:灰色,

结合CSS3的一些选择器,如html:first-child,body:nth-of-type(1),衍生出更多的hack方式,具体的可以参考下

CSS hack利弊

一般情况下,我们尽量避免使用CSS hack,但是有些情况为了顾及用户体验实现向下兼容,不得已才使用hack。比如由于IE8及以下版本不支持CSS3,而我们的项目页面使用了大量CSS3新属性在IE9/Firefox/Chrome下正常渲染,这种情况下如果不使用css3pie或htc或条件注释等方法时,可能就得让IE8-的专属hack出马了。使用hack虽然对页面表现的一致性有好处,但过多的滥用会造成html文档混乱不堪,增加管理和维护的负担。相信只要大家一起努力,少用、慎用hack,未来一定会促使浏览器厂商的标准越来越趋于统一,顺利过渡到标准浏览器的主流时代。抛弃那些陈旧的IE hack,必将减轻我们编码的复杂度,少做无用功。
最后补上一张引自国外某大牛总结的CSS hack表,这时一张6年前的旧知识汇总表了,放在这里仅供需要时候方便参考。


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值