解决移动端CSS Sprites展示不全问题

最近工作中制作移动端活动页面的时候,由于图片较多,因此频繁使用到CSS Sprites,此时会遇到了一个常见问题——在不同分辨率下,background-position定位的图片的边缘有可能被裁剪,显示不全。

对比几种CSS Sprites的适配方法

目前为止,我知道并尝试过的适配方法有如下几种:

  • rem
  • 百分比
  • zoom
  • transform scale

通过制作demo,我们对一张CSS Sprites进行展示,通过上述几种方法,在iphone6下就出现了图片展示不全的问题(红框中的图片的边缘被裁剪),如下图:

各适配方法结果对比

由于rem、百分比单位最终都会被浏览器解析成px进行渲染,分辨率不同生成的px值一般会存在小数点,而浏览器对小数点的解析也不一样。IE7-和safari会对小数点取整,而IE8+、chrome、firefox等浏览器则会四舍五入。因此浏览器对rem、百分比单位转换成px时,很容易因为1px的差而导致CSS Sprites定位不准而造成边缘被裁剪的现象。

在以往的项目中,用得最多的是百分比,其精度相对于rem较好点,出现图标被裁剪的情况较少。但是在这个项目中,利用百分比依旧不如人意。

百分比定位参考文章:http://zhangruojun.com/backgroud-positionde-bai-fen-bi-zhi/?utm_source=tuicool&utm_medium=referral

之后尝试了使用zoom的方法,直接对图标进行缩放,效果却和rem差不多。

rem和zoom的解决方案

针对上面的rem和zoom方法的解决方案是,制作CSS Sprite时图标之间相隔远一点,css中图标尺寸设置大一点,background-position的值相对原值小一点。
比如,正常设置如下:

// rem
.icon{
      width: 0.2rem;
      height: 0.2rem;
      background-position: -1rem -0.8rem;
}

// zoom
.icon{
      width: 20px;
      height: 20px;
      background-position: -100px -80px;
}

采用解决方案后的设置如下:

// rem
.icon{
      width: 0.24rem;
      height: 0.24rem;
      background-position: -0.98rem -0.78rem;
}

// zoom
.icon{
      width: 24px;
      height: 24px;
      background-position: -98px -78px;
}

效果图如下,基本上解决了图标被裁剪的问题:

不过上述解决方案,我认为在代码上总是要想着时刻加减原值,而且后期维护的时候如果忽略了该解决方法,很容易又会出现上述问题。此外,在页面布局上,图标在页面中的位置容易出现1px的偏差,在元素布局的时候也需要注意这个误差。

transform scale方法

由zoom缩放自然联想到了transform里的scale缩放方法。
关于zoom和transform scale的区别可以查看这两篇文章:
http://www.zhangxinxu.com/wordpress/2015/11/zoom-transform-scale-diff/
http://www.cnblogs.com/Hchun/p/5291400.html

transform scale方法代码:

.icon{
      width: 20px;
      height: 20px;
      background-position: -100px -80px;
}
//设计稿宽度为640px,所有值均和设计稿取值一致
@media only screen and (max-width: 320px){
     .icon{-webkit-transform:scale(0.5);transform:scale(0.5);}
}
效果图

单纯地用transform scale方法,确实可以较完美地解决边框被裁剪的问题,但是其在页面中的位置却不对了。探究发现有两个原因:

  1. transform scale默认情况下是相对于元素中心进行缩放的。
  2. transform scale只会对元素本身进行缩放,在页面渲染的时候,会先渲染元素原始的大小,再进行缩放。缩放的时候不会再引起页面的重绘,因此元素原始尺寸有多大,就会占据页面多大的空间,和缩放无关。

那有没有解决方案,可以保留transform scale完美呈现图标的优点,又能够实现页面精准布局的方法呢?

transform scale & :before方法

如果给元素再包裹一层容器,让父容器大小和元素一致,再让元素脱离文档流,始终相对于父容器定位呢?理论上是可以实现的,但是这样会多增加一层标签。因此,自然想到了伪元素:before和:after,让伪元素展示图标。
具体代码如下:

.icon{
      width: 0.2rem;
      height: 0.2rem;
      position: relative;
}
.icon:before{
      width: 20px;
      height: 20px;
      background-position: -100px -80px;
      position: absolute;
      left: 0;
      top: 0;
      -webkit-transform-origin: 0 0; //让元素相对于左上角进行缩放
      transform-origin: 0 0;
}
@media only screen and (max-width: 320px){
     .icon:before{-webkit-transform:scale(0.5);transform:scale(0.5);}
}

这样基本上就能保证图标完整且位置准确。

不过这个方法最大的不足,是增加了css里面的代码量。

关于rem、zoom、transform scale几种方法实现移动端的CSS Sprites,其优缺点都是显而易见的,在项目中可以根据具体情况来权衡采用哪种方法。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • 问答题47 /72 常见浏览器兼容性问题与解决方案? 参考答案 (1)浏览器兼容问题一:不同浏览器的标签默认的外补...
    _Yfling阅读 14,680评论 1 92
  • H5页面窗口自动调整到设备宽度,并禁止用户缩放页面//一、HTML页面结构 // width 设置viewp...
    tiandashu阅读 16,793评论 0 9
  • CSS 是什么 css(Cascading Style Sheets),层叠样式表,选择器{属性:值;属性:值}h...
    崔敏嫣阅读 5,342评论 0 5
  • 剧中的欧阳菁是京州市市委书记李达康的妻子,同时她还是城市银行的副行长。这样的头衔对于任何一个女人来说都是可望而不可...
    若水17阅读 9,842评论 0 15
  • 将就一辈子的婚姻 ——冬风欲晓 说起“将就”这个词,想来它是在“当你生命中出现过那个人时,其他人都会成为将就,而我...
    冬风欲晓阅读 3,030评论 0 1