使用CSS3 Gradients创建图片占位符
本文根据Nico Hagenburger的《Use CSS3 Gradients to Create Placeholders for Images》一文整理
最典型的问题是在画册制作中,没有显示出足够多图片:
解决方案有很多种,你可以在后面直接留空白区域;你也可以添加额外的html标签作为占位符。第一种方案觉得还可以,但第二种解决方案感觉会让你的代码不干净。或者给画册元素添加一个背景图像,但这样会增加http的请求数。
CSS3渐变就像是背景图像。只需要把他的起始色和终止色设置为相同颜色,这样就不会产生一个渐变的背景。然后通过与background-size
和background-position
的配合,可以生成图像占位符。
第一步:用渐变添加背景
把图片先全部删除了,打算加个背景:
.step-1 {
background: linear-gradient(#DBE0DF, #DBE0DF);
}
第二步:设置尺寸
使用background-size
将渐变(渐变制作的背景图片)尺寸设置和图片尺寸一样(156px)。为了防止渐变像第一步那样填充整个容器,需要设置background-repeat
为no-repeat
。
.step-2 {
background: linear-gradient(#DBE0DF, #DBE0DF) no-repeat;
background-size: 156px 156px;
}
第三步:设置渐变图像位置
要保持渐变图位置和图像占位符保持一致,这个时候需要使用background-origin
属性,并且将其设置为content-box
用来设置背景图片起始位置从content的外边缘开始显示。
.step-3 {
background: linear-gradient(#DBE0DF, #DBE0DF) no-repeat;
background-size: 156px 156px;
background-origin: content-box;
}
第四步:重排(横向排列)
使用space
替代repeat
。让背景图片有点类似于text-align: justify
效果:
.step-4 {
background: linear-gradient(#DBE0DF, #DBE0DF) space;
background-size: 156px 156px;
background-origin: content-box;
}
完美的,对不对?你使用的是Chrome浏览器,对不对?让我们回到以前的特性。
第五步:重排(repeat)
另外一个解决方案,就是使用多背景,也是使用渐变制作的多背景,只不过这里我们需要手工给每个背景定位。
.step-5 {
background: linear-gradient(#DBE0DF, #DBE0DF) 0 0,
linear-gradient(#DBE0DF, #DBE0DF) 166px 0,
linear-gradient(#DBE0DF, #DBE0DF) 332px 0,
linear-gradient(#DBE0DF, #DBE0DF) 498px 0,
linear-gradient(#DBE0DF, #DBE0DF) 664px 0;
background-repeat: no-repeat;
background-size: 156px 156px;
background-origin: content-box;
}
现在在大多数浏览器他是完美的,在旧的浏览器中能看到一个透明的背景。他只是一个图像占位符,总比加载图像拖慢网站速度来得强吧。
但代码看起来还是蛮复杂的,我们可以尝试使用Sass来处理。
第六步:Sass制作(DRY)
@function background-placeholder-images($color, $size, $gap, $count) {
$result: ();
@for $i from 1 through $count {
$x: ($gap + $size) * ($i - 1);
$result: append($result, linear-gradient($color, $color) $x 0, comma);
}
@return $result;
}
@mixin background-placeholders($color, $size, $gap, $count) {
background: background-placeholder-images($color, $size, $gap, $count);
background-repeat: no-repeat;
background-size: $size $size;
background-origin: content-box;
}
.step-6 {
@include background-placeholders($color: #DBE0DF, $size: 156px, $gap: 10px, $count: 5);
}
这一步我们分解一下:
定义函数
为了实现gradient制作图像占位符,特意通过Sass的@function
函数功能创建了一个background-placeholder-images
函数。并且给这个函数传了几个参数:
-
$color
:这个主要实现图像占位符的背景图像颜色。前面我们说过了,图像占位符使用的是CSS3的渐变功能制作的,而且起始和终止色是相同的,所以在这里定义一个颜色的参数$color
。 -
$size
:每个占位符需要一个尺寸,而且这个尺寸大小和图像的尺寸是一致的。不过有一个缺陷,我们这里使用的是一个正方形图像,如果图像尺寸不是正方形,此处需要定义两个尺寸变量。个人建议使用$size-width
和$size-height
。如此一来,不管图像尺寸是不是正方形,我们都能很好的控制。后面我们将实现一个不是正方形图形的一个案例。 -
$gap
:这个参数主要是用来设置占位符与占位符之间的间距。你可以将此想像成是一个Grid。那么在列与列之间有一个列间距,那么$gap
就是这个列间距。 -
$count
:这个参数很好理解,他就是图像占位符的个数。
因为我们在制作图像占位符时,使用渐变制作的背景图像,而且结合了多背景功能,因此在整个背景图像中会有多个line-gradient
,而具体会有多少个,这需要我们的$count
参数决定。如此一来,在Sass中我们就需要使用到list
特性。所以在函数的最开始地方,先预设置了一个空的列表$result
:
$result:();
在Sass中,我们可以通过给变量赋予一个空值,来初始化一个列表。详细介绍请阅读早前博文《理解Sass的list》中“创建一个Sass的list”一节。
由于有多个背景图像,而且每个背景图像的background-position
位置是不一样的,而且这个个数也是未知的,所以我们需要通过Sass的遍历功能来遍历。在这里使用了Sass中的@for
指令。
@for $i from 1 through $count {
$x: ($gap + $size) * ($i - 1);
$result: append($result, linear-gradient($color, $color) $x 0, comma);
}
如果您从未接触过Sass的指令特性,建议您先阅读《Sass控制命令:@if,@for,@each和@while》和《了解Sass的控制命令》。——@大漠
在这个@for
循环中有一个数学计算:
$x: ($gap + $size) * ($i - 1);
这个计算,主要用来控制背景图像的水平位置,也就是background-position
在X轴的起始点,而Y轴的起始点始终是在0处。我们来看一张图:
接下来通过append()
函数将得到的渐变图像值再插入到$result
列表。
特别需要注意的是,在使用append()
函数插入渐变图像值到$result
列表中时,使用的是逗号(,
),那么在Sass中主要使用comma
和space
来区分。其中comma
值指定列表中的列表项值之间使用逗号(,)分隔, space
值指定列表中的列表项值之间使用空格( )分隔。
所以在上面的代码中,最后有一个comma
参数。详细介绍可以点击这里中jion()
函数一节。
实现渐变图像的函数功能有了,我们还有其他的参数需要设置,在此,通过@mixin
创建了一个background-placeholders
混合,并且传给了$color
、$size
、$gap
和$count
几个参数,而且这几个参数所起作用与background-placeholder-images()
函数功能是一样的。
@mixin background-placeholders($color, $size, $gap, $count) {
background: background-placeholder-images($color, $size, $gap, $count);
background-repeat: no-repeat;
background-size: $size $size;
background-origin: content-box;
}
到这一步,我们使用Sass制作图像占位符的功能就完成了,在需要使用的地方调用我们定义好@mixin backround-placeholders
:
.step-6 {
@include background-placeholders($color: #DBE0DF, $size: 156px, $gap: 10px, $count: 5);
}
编译出来的CSS:
.step-6 {
background: linear-gradient(#dbe0df, #dbe0df) 0px 0, linear-gradient(#dbe0df, #dbe0df) 166px 0, linear-gradient(#dbe0df, #dbe0df) 332px 0, linear-gradient(#dbe0df, #dbe0df) 498px 0, linear-gradient(#dbe0df, #dbe0df) 664px 0;
background-repeat: no-repeat;
background-size: 156px 156px;
background-origin: content-box; }
前面说了,我们这个功能只适合于图像是正方形的,也就是图像占位符也是正方形的,一旦换成长方形就不适用了。那么我们在此基础上做一定的修改,将$size
参数换成$size-widt
和$size-height
:
@function background-placeholder-images($color, $size-width,$size-height, $gap, $count) {
$result: ();
@for $i from 1 through $count {
$x: ($gap + $size-width) * ($i - 1);
$result: append($result, linear-gradient($color, $color) $x 0, comma);
}
@return $result;
}
@mixin background-placeholders($color, $size-width,$size-height, $gap, $count) {
background: background-placeholder-images($color, $size-width,$size-height, $gap, $count);
background-repeat: no-repeat;
background-size: $size-width $size-height;
background-origin: content-box;
}
.step-7 {
@include background-placeholders($color: #DBE0DF, $size-width: 250px,$size-height:156px, $gap: 10px, $count: 4);
}
注意其中的变化。最终效果如下:
我们回到原文中。
最后,通过Sass我们实现了自动化,不需要人工手动去计算。除了这个案例之外,在Homify的样式指南中,提供了更多复杂的案例,有兴趣的同学可以从中找出更多更有用的知识。希望能将你的所得与我们一起分享。
译者手语:整个翻译依照原文线路进行,并在翻译过程略加了个人对技术的理解。如果翻译有不对之处,还烦请同行朋友指点。谢谢!
如需转载烦请注明出处:
英文出处:http://www.hagenburger.net/BLOG/background-placeholders-with-gradients.html
中文译文:https://www.fedev.cn/preprocessor/background-placeholders-with-gradients.html
nike air max 1 yeezy