本文分享下我在项目中积累的IE8+兼容性问题的解决方法。根据个人实践经验,若是你在写HTML/CSS时候是按照W3C推荐的方式写的,而后下面的几点都关注过,那么基本上很大一部分IE8+兼容性问题都OK了(这里的IE8+主要是指IE8,据我的目测,IE9+的渲染效果已经很是好了)。css
前期准备
测试IE兼容性必需要在Windows中测,并且是Win7+,由于WinXP最高只支持IE8,IE9就呵呵啦!大部分作Web的童鞋都不是使用Windows作为开发环境,要么是Linux发行版,要么是Mac OS。怎么办?通常有2种方法:html
- 开Windows虚拟机
- 将开发环境暂时切换到Windows
若是你的机器足够快,我推荐前一种方式。但若是机器不行,开虚拟机就会很卡。若是你是Pythonista,我以前写的一篇日志《在Windows中搭建Python Web开发环境》可能会对你有点用处。前端
我以为能够把精力集中在这几个浏览器上:IETester(IE8-IE9)、360浏览器、搜狗浏览器、Chrome。IETester测完了建议再用真实的IE八、IE9过一遍,以防万一。html5
DOCTYPE
首先须要确保你的HTML页面开始部分要有DOCTYPE声明。DOCTYPE告诉浏览器使用什么样的HTML或XHTML规范来解析HTML文档,具体会影响:python
- 对标记、attributes 、properties的约束规则
- 对浏览器的渲染模式产生影响,不一样的渲染模式会影响到浏览器对于CSS 代码甚至 JavaScript 脚本的解析
DOCTYPE是很是关键的,目前的最佳实践就是在HTML文档的首行键入:jquery
<!DOCTYPE html>
对于DOCTYPE的具体阐述就不展开了,能够参考:《正确使用DOCTYPE》、《CS002: DOCTYPE 与浏览器模式分析》。css3
使用meta标签调节浏览器的渲染方式
IE8中有一个“兼容性视图”的概念,当初IE8发布时,相对于IE6/7已经作出了很是大的改进,可是不少老站点仅针对IE6/7进行了优化,使用IE8渲染反而会一团糟。为了照顾这些苦逼的前端工程师,IE8加入了“兼容性视图”功能,这样的话就能够在IE8中使用IE6或IE7的内核渲染页面。这个固然不是咱们想要的,因此须要使用meta标签来强制IE8使用最新的内核渲染页面,代码以下:git
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
IE=edge
表示强制使用IE最新内核,chrome=1
表示若是安装了针对IE6/7/8等版本的浏览器插件Google Chrome Frame(可让用户的浏览器外观依然是IE的菜单和界面,但用户在浏览网页时,实际上使用的是Chrome浏览器内核),那么就用Chrome内核来渲染。关于此meta标签的具体说明,可参见StackOverflow上的精彩回答。github
国内存在不少双核浏览器好比360浏览器、搜狗浏览器,它们是怎么决定某页面到底使用哪一种内核渲染?下面引用一段360浏览器v6新特性的官方说明:web
因为众所周知的状况,国内的主流浏览器都是双核浏览器:基于Webkit内核用于经常使用网站的高速浏览。基于IE的内核用于兼容网银、旧版网站。以360的几款浏览器为例,咱们优先经过Webkit内核渲染主流的网站,只有小量的网站经过IE内核渲染,以保证页面兼容。在过去很长一段时间里,咱们主要的控制手段是一个几百k大小网址库,一个经过长期人工运营收集的网址库。
尽管咱们努力经过用户反馈、代码标签智能判断技术提升浏览器的自动切核准确率。可是在不少状况下,咱们仍然没法达到百份百正确。所以,咱们新增长了一个控制手段:内核控制Meta标签。只要你在本身的网站里增长一个Meta标签,告诉360浏览器这个网址应该用哪一个内核渲染,那么360浏览器就会在读取到这个标签后,当即切换对应的内核。并将这个行为应用于这个二级域名下全部网址。
解决方法360已经告诉咱们了,经过meta标签的方式建议其使用Webkit,代码以下:
<meta name="renderer" content="webkit">
我没有作细致的调查,不知道其余的双核浏览器是否支持此特性。
Media Query
IE8彷佛没法识别Media Query,因此须要hack一下啦!推荐采用Respond.js解决此问题,具体方法参见它的文档便可。
实现CSS3的某些特性
IE8不支持CSS3的不少新特性,不过咱们可使用一些比较成熟的hack方法,我采用的是CSS3 PIE,它支持的特性有这些:border-radius、box-shadow、border-image、multiple background images、linear-gradient等。
特别注意:请必定阅读CSS PIE给出的Know Issues。
识别HTML5元素
若是你在前端代码中使用了HTML5的新标签(nav/footer等),那么在IE中这些标签可能没法正常显示。我使用html5shiv,具体使用方法见文档。
关于max-width
还有一个在IE8中常常遇到的问题就是max-width,网页中图片的尺寸可能比较宽,我会给它设置max-width: 100%
来限制其宽度最大为父容器的宽度,可是有时候却不奏效,慢慢摸索才得知IE解析max-width所遵循的规则:严格要求直接父元素的宽度是固定的。经实验发现Chrome所遵照的规则比IE松一些,因此这个问题应该不归属为IE兼容性问题,不过我仍是提一下吧。分享两个我遇到的场景:
(1)td中的max-width
若是针对td中的img元素设置max-width: 100%
,在IE和Firefox你会发现不奏效,而在Chrome中倒是能够的。经查询发现须要给table设置table-layout: fixed
,对此属性的具体解释见W3School。
(2)嵌套标签中的max-width
以下的HTML结构:
<div class="work-item"> <a href="#" class="work-link"> <img src="sample.jpg" class="work-image img-responsive"> </a> </div>
最外层元素.work-item
设置了固定宽度,可是对img设置max-width为100%却无效,后来才发现须要再对a标签设置width: 100%
,这样才能使最内层的img标签充满整个div。
嵌套inline-block下padding元素重叠
HTML代码:
<ul>
<li><a>1</a></li> <li><a>2</a></li> <li><a>3</a></li> </ul>
CSS代码:
ul li{ display: inline-block; } ul li a{ display: inline-block; padding: 10px 15px; }
按理来讲a标签之间的距离应该是30px,但在IE8中出现了重叠,只有15px。这里和这里也提到了一样的问题。个人解决方法是使用float: left
替代display: inline-block
实现水平布局。
placeholder
IE8下不支持HTML5属性placeholder,不过为解决此问题的js插件挺多的,好比:jquery-placeholder。
last-child
first-child是CSS2的内容,可是last-child就不是了,因此IE8不买帐。推荐的作法不是使用last-child,而是给最后一个元素设置一个.last
的class,而后对此进行样式设置,这样就所有兼容了。
background-size: cover
若是你想使用background-size: cover
设置全屏背景,很遗憾IE8办不到...但可使用IE独有的AlphaImageLoader滤镜来实现,添加一条以下的CSS样式:
filter: progid:DXImageTransform.Microsoft.AlphaImageLoader(enabled=Enabled, sizingMethod=Size , src=URL)
将sizingMethod设置为scale就OK了。
还没完,若是你在此背景之上放置了连接,那这个连接是没法点击的。通常状况下的解决办法是为连接或按钮添加position:relative
使其相对浮动。
filter blur
CSS3中提供支持滤镜效果的属性filter,好比支持高斯模糊效果的blur(相似iOS7的效果):
filter: blur(10px); -webkit-filter: blur(10px); -moz-filter: blur(10px);
IE8对filter: blur(10px)
的显示效果是对HTML元素进行小范围的模糊处理,这个效果并非高斯模糊,要想支持高斯模糊,须要以下设置:
filter: progid:DXImageTransform.Microsoft.Blur(PixelRadius='10');
在实践中发现一个坑就是,全部position: relative
的元素都不会生效。
其余的发现是,IE9对filter: blur(10px)
无效,而对filter: progid:DXImageTransform.Microsoft.Blur(PixelRadius='10');
是针对元素小范围的模糊效果。