饥人谷技术博客

浏览器兼容

2016-07-31  本文已影响217人  进击的阿群

1. 如何调试 IE 浏览器?

  1. IE7及以上版本有调试台,可以按F12启动:
    优点:权威;
    缺点:不方便,正常情况下只能安装一个版本IE。


    IE11调试台
  2. 模拟器模拟不同版本IE,微软官方有诸如virtual pc、Expression Web SuperPreview等,在此以ietester为例:
    优点:集成需要的所有版本IE;
    缺点:效果是模拟出来的,权威性不足。


    ietester
  3. 虚拟机,安装带有不同版本IE的系统:
    优点:权威,而且多版本均能调试;
    缺点:占空间,占内存,但是不太影响使用。
virtualbox虚拟机IE678

2. 什么是CSS hack?在 CSS 和 HTML里如何写 hack?在 CSS 中 ie6、ie7的 hack 方式?

  1. CSS属性前缀法
  2. 选择器前缀法
  3. IE条件注释法(即HTML头部引用if IE)Hack,实际项目中CSS Hack大部分是针对IE浏览器不同版本之间的表现差异而引入的。
.hack {
  color: silver; /* 所有浏览器 */
  color: yellow !important; /* 除IE6外所有浏览器 */
  *color: red; /* IE6,IE7 */
  +color: green; /* IE6,IE7 */
  _color: blue; /* 只有IE6 */
  color: gray\9; /* IE6,IE7,IE8,IE9,IE10 */
  color: pink\0; /* IE8,IE9,IE10 */
  color: purple\9\0; /* IE9,IE10 */
}
  *html #selector {} /* 只对IE6生效 */
  *+html #selector {} /* 只对IE7生效 */
  @media screen\9 { .selector {  property: value; } } /* 只对IE6、7生效 */
  @media \0screen {body { background: red; }} /* 只对IE8生效 */
  @media \0screen\,screen\9{body { background: blue; }} /* 只对IE6,IE7,IE8有效 */
  @media screen\0 {body { background: green; }} /* 只对IE8,IE9,IE10生效 */
  @media screen and (min-width:0\0) {body { background: gray; }} /* 只对IE9,IE10生效 */

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

选择器hack.jpg

只在IE下显示:

<!--[if IE]>
    <p>这段代码只有IE浏览器识别</p>
<![endif]-->

只在IE6显示:

<!--[if IE 6]>
    <p>这段文字只在IE6浏览器显示</p>
<![endif]-->

只在IE6以上版本显示:

<!--[if gte IE 6]>
<p>这段文字只在IE6及以上版本IE浏览器显示</p>
<![endif]-->

只在IE8上不生效:

< !--[if ! IE 8 ]>
<p>如果不是IE8,则生效</p>
<![endif]-->

非IE生效:

<!--[if ! IE]>
<p>如果不是IE,则生效</p>
<![endif]-->

操作符的使用:

| 项目 | 范例 | 说明 |
| :-------- : | :-----: | :----: |
| ! | [if !IE] | NOT运算符。 |
| lt | [if lt IE 5.5] | 小于运算符。如果第一个参数小于第二个参数,则返回true。 |
| lte | [if lte IE 6] | 小于或等于运算。如果第一个参数是小于或等于第二个参数,则返回true。 |
| gt | [if gt IE 5] | 大于运算符。如果第一个参数大于第二个参数,则返回true。 |
| gte | [if gte IE 7] | 大于或等于运算。如果第一个参数是大于或等于第二个参数,则返回true。 |
| ( ) | [if !(IE 7)] | 子表达式运算符。在与布尔运算符用于创建更复杂的表达式。 |
| & | [if (gt IE 5)&(lt IE 7)] | AND运算符。如果所有的子表达式计算结果为true,返回true。 |

.hack {
 _color: silver;
}
*html .hack {
  color: silver;
}
<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <title>task13</title>
    <style type="text/css">
      body {
        background: red;
      }
      body.ie6 {
        background: silver;
      }
    </style>
  </head>
  <!--[if IE 6]>
  <body class="ie6">
  <![endif]-->
  <!--[if ! IE]> -->
    <body>
  <!-- <![endif]-->
    <h1>IE6下的body背景为红色</h1>
  </body>
</html>  

效果图:

IE6效果图 IE11效果图
.hack {
    *color: red;  /* 只有IE7生效 */
}
      *+html body {
            color: orange; /* 只有IE7生效 */
}
<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <title>task13</title>
    <style type="text/css">
      body {
        background: red;
      }
      body.ie6 {
        background: silver;
      }
      body.ie7 {
        background: orange;
      }
    </style>
  </head>
  <!--[if IE 6]>
  <body class="ie6">
  <![endif]-->
  <!--[if IE 7]>
  <body class="ie7">
  <![endif]-->
  <!--[if ! IE]> -->
    <body>
  <!-- <![endif]-->
    <h1>IE6下的body背景为红色</h1>
  </body>
</html>

效果图:

IE7条件注释效果图

参考
browserhacks
史上最全的CSS hack方式一览
注释——维基百科


3. 列举几种浏览器兼容问题

inline-block兼容性

可以看出inline-block对于IE6、IE7并不支持,解决方法是优雅降级,将display属性值在IE6、7下写为display: inline;代替:

<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <title>task13</title>
    <style type="text/css">
      div {
        display: inline-block;
        /**display: inline;*/          /* 未应用hack */
      }
    </style>
  </head>

    <body>
    <div>hello</div>
    <div>world!</div>
  </body>
</html>

未应用hack的IE6效果:

未应用hack的IE显示

应用hack的IE6效果:

      div {
        display: inline-block;
        *display: inline;           /* 应用hack */
      }
IE6hack显示 opacity.png
      div {
        background: red;
        opacity: 0.5;
        filter: alpha(opacity=50); /* 兼容IE */
      }
.selector {
        height:auto !important; 
        height:100px; 
        min-height:100px; 
}
* 方法二:overflow:visible属性实现: 
.selector {
        min-height:100px; 
        _height:100px; 
        overflow:visible; 
}

第二种方法说明一下:

min-height
  * {
        margin: 0;
        padding: 0;
}

这个是最常见的也是最易解决的一个浏览器兼容性问题,几乎所有的CSS文件开头都会用通配符*来设置各个标签的内外边距是0。

双外边距浮动bug

解决方法:将元素的display属性设置为inline即可。

.selector {
        float: left;
        margin: 20px;
        display: inline;
}

例子:

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <title>双外边距bug</title>
    <style type="text/css">
        * {
            margin: 0;
            padding: 0;
        }
        .box1{
            background: red;
            width: 100px;
            height: 50px;
            float: left;
            margin-left: 20px;
            margin-top: 20px;
            /*设置display修复双外边距bug*/
            /*display: inline;*/
        }
        .box2{
            background: blue;
            width: 100px;
            height: 50px;
            float: left;
            margin-left: 20px;
            margin-top: 20px;
        }
    </style>
</head>
<body>
    <div class="box1">
    </div>
    <div class="box2">
    </div>
</body>
</html>
双边距浮动bug修复前.png 双边距浮动bug修复后.png

参考常见浏览器兼容性问题与解决方案


4. 针对兼容、多浏览器覆盖有什么看法?渐进增强和优雅降级是什么意思?

  • 区别:优雅降级是从复杂的现状开始,并试图减少用户体验的供给,而渐进增强则是从一个非常基础的,能够起作用的版本开始,并不断扩充,以适应未来环境的需要。降级(功能衰减)意味着往回看;而渐进增强则意味着朝前看,同时保证其根基处于安全地带。

5. reset.css和normalize.css分别是做什么的?为什么推荐使用 nomalize.css?

参考
Normalize.css 与传统的 CSS Reset 有哪些区别?——知乎
来,让我们谈一谈 Normalize.css


6. IE盒模型和标准盒模型有什么区别? 怎样使 IE678使用标准盒模型?box-sizing:border-box有什么作用?

W3C盒模型&IE盒模型.gif
<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <title></title>
    <style type="text/css" media="screen">
        .container1 {
            box-sizing: border-box;
        }
        .container1,.container2 {
            border: 5px solid black;
            width: 100px;
            height: 100px;
            padding: 10px;
            background-color: red;
            text-align: center;
            vertical-align: middle;
            margin: 60px;
        }
    </style>
</head>
<body>
    <div class="container1"></div>
    <div class="container2"></div>
</body>
</html>

效果图:

IE盒模型和标准盒模型

操作

<!DOCTYPE html>                <!-- 标准模式 -->
<html>
  <head>
    <meta charset="utf-8">
    <title>task13</title>
    <style type="text/css">
      .ct1,.ct2 {
        width: 100px;
        height: 100px;
        border: 5px solid;
        background: red;
      }
    </style>
  </head>
  <body>
    <div class="ct1">1</div>
    <div class="ct2">2</div>
  </body>
</html>

在IE6下的表现:

IE6盒模型

在IE7下的表现:

IE7盒模型

在IE8下的表现:

IE8盒模型

如图所示,可以看出IE678在盒模型的表现方面一致,没有差别。

<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <title>task13</title>
    <style type="text/css">
      .ct1,.ct2,.ct3 {
        width: 100px;
        height: 100px;
        border: 5px solid;
        background: red;
        margin-top: 20px;
        display: inline-block;
      }
    </style>
  </head>
  <body>
    <div class="ct1">1</div>
    <div class="ct2">2</div>
    <a href="#" class="ct3">3</a>
  </body>
</html>

在IE6下的表现:

IE6下的inline-block

在IE7下的表现:

IE7下的inline-block

在IE8下的表现:

IE8下的inline-block

如图所示,IE8正常显示,IE67块级元素不能解析inline-block,而IE67的行内元素能解析,为此查兼容性如下:

inline-block.png

在最下面的“Notes”里有说明此问题,所以实验正确。

<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <title>task13</title>
    <style type="text/css">
      .ct1,.ct2 {
        max-width: 100px;
        height: 100px;
        border: 5px solid;
        background: red;
      }
    </style>
  </head>
  <body>
    <div class="ct1">这是一段test,这是一段test,这是一段test,
    这是一段test,这是一段test,这是一段test,这是一段test,这是一段test,
  这是一段test,这是一段test,这是一段test,这是一段test,这是一段test,
这是一段test,这是一段test,这是一段test,这是一段test,</div>
  </body>
</html>

IE6下的表现:

IE6下的max-width

IE7下的表现:

IE7下的max-width

IE8下的表现:

IE8下的max-width

在上述min-height的兼容性中,也包括了max-width的兼容性,在note注释里写着IE7不支持inherit属性值,IE8下max-width和overflow: scroll/auto并用时,会存在bug,故使用时要注意。

总结:

兼容性问题是必须要考虑的,不过不能过分考虑,通过适当的手段优雅降级,通常能够达到很好的效果,normalize.css是利器,属性前缀法经常用到,而bug千差万别,要一一排查会有些麻烦,把兼容样式放在一个样式表中,方便阅读并且维护,理性考虑兼容。


本文版权归本人和饥人谷所有,转载请注明来源,谢谢!

上一篇 下一篇

猜你喜欢

热点阅读