最近在项目中使用了Bootstrap,而且项目要求兼容IE8。项目中使用bootstrap的默认样式,然后在此基础上另外使用一个css文件编写自定义的样式。原本以为在页面中加入Respond.js可以让Bootstrap的样式在IE8下自动解析出来,但是发现有的自定义css起作用了,有的没有起作用(非CSS3特效),非常奇怪。
上网查询Respond失效原因,非常多,总结起来有这几点:
- 跨域问题
- CSS文件和js文件标签书写顺序
- 文件访问方式(http://还是file://)
- 样式是否放在CSS文件中
这几点都不符合我实际的环境,可以排除,这些方法都不适用。那问题出在什么地方?
查看Respond.js的Github主页,在工作原理章节发现了这句话:
each media query block is appended to the head in order via style elements, and those style elements are enabled and disabled (read: appended and removed from the DOM) depending on how their min/max width compares with the browser width.
意思就是Respond.js自动将带有@media的css块解析后放到html文件的head中,让其在渲染中起作用。看到这里基本上就明白了到底是什么地方导致自定义样式不起作用了。
原因在于bootstrap中很多样式都是写在@media的块中的,比如:
/* quick sidebar top position fix for mobile view */
@media (max-width: 480px) {
/* 480px */
.page-quick-sidebar-wrapper {
top: 92px;
}
.page-quick-sidebar-toggler {
top: 65px;
}
}
假如在自定义css中改写这段的效果,原来的写法是:
.page-quick-sidebar-wrapper {
top: 100px;
}
.page-quick-sidebar-toggler {
top: 100px;
}
虽然自定义的css文档标签是放在后面的,但是实际上并没有见效,因为respond将上述@media中的css样式提取并放置在html的head中,相当于是放置在自定义样式的后面了,当然无法起作用。正确的写法是:
@media (max-width: 480px) {
/* 480px */
.page-quick-sidebar-wrapper {
top: 100px;
}
.page-quick-sidebar-toggler {
top: 100px;
}
}
在自定义的css中也需要使用@media块包裹起来,这样Respond.js在解析时也会自动将自定义的样式与默认样式按照顺序放在head中,显示效果就正确了。
实际验证一下,代码结构如下:
+--respond.html
|--1.css
|--2.css
respond.html代码:
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width,initial-scale=1.0">
<link rel="stylesheet" type="text/css" href="1.css">
<link rel="stylesheet" type="text/css" href="2.css">
<script src="jquery.min.js"></script>
<!-- HTML5 Shim and Respond.js 用来支持IE8上的media queries和HTML5元素 -->
<!-- WARNING: Respond.js doesn't work if you view the page via file:// -->
<!--[if lt IE 9]>
<script src="respond.min.js"></script>
<![endif]-->
</head>
<body>
</body>
1.css代码:
@media screen and (min-width: 300px) {
body {
background-color:lightblue;
}
}
2.css代码:
@media screen and (min-width: 300px) {
body {
background-color:lightgreen;
}
}
经过测试,页面背景为浅绿色,测试结果:
证明respond.js正确执行,如果把2.css代码更改为:
body {
background-color:lightgreen;
}
页面背景为浅蓝色,测试结果:
2.css中新定义的样式没有起作用。
总结:以后在使用Bootstrap之类样式时,如果要自定义样式,最好查看清楚对应的样式在Bootstrap的默认样式文件中是否使用了@media,如果是的话,最好也使用相同的媒体查询条件将自定义样式包裹起来,以免在使用Respond.js兼容低版本IE浏览器时出现样式失效的情况。