直到前天同事的技术分享,我才突然觉得我好像并不懂 css,只会实现,不会就 Google,但是从来没有去真正的了解过其中的原理,惭愧。
所以重看 css 和 js 都是必须要做的事。
x (baseline)
我之前一直没有了解过的”x”,在各种内联模型中,涉及排版或者对齐时都需要用到基线(baseline),比如line-light
行高的定义就是两基线的间距,vertical-align
的默认值就是基线。
那么最普遍的就是字母基线(x
的下边缘线):
- x-height: 小写 x 字母的高度
- ascender height: 上下线高度
- cap height: 大写字母高度
- median: 中线
- descender height: 下行线高度
在 css 内vertical-align: middle
就与x-height
有关,其中 middle 与上述 median 并不同,在规范中对middle
的解释:
middle: This identifies a baseline that is offset from the alphabetic baseline in the shift-direction by 1/2 the value of the x-height font characteristic. The position of this baseline may be obtained from the font data or, for fonts that have a font characteristic for “x-height”, it may be computed using 1/2 the “x-height”. Lacking either of these pieces of information, the position of this baseline may be approximated by the “central” baseline.
middle 指的是基线往上 1/2 “x-height”高度。可以近似看做字母 x 交叉点那个位置。
所以vertical-align: middle
并不是绝对的垂直居中对齐。
css 内的ex
单位:一个相对单位,指小写字母 x 的高度。
实用:借助ex
实现 icon 上下垂直居中的效果(必须为内联元素),优点在于不受字体字号影响。
.icon-arrow {
display: inline-block;
width: 20px;
height: 1ex;
background: url(arrow.png) no-repeat center;
}
border
border-color: 如果设置 border 宽度为 Xpx,那么可以在 border 上适应 X 种颜色,每种颜色显示 1px 的宽度。如果说你的 border 的宽度是 10 个像素,但是只声明了 5 或 6 种颜色,那么最后一个颜色将被添加到剩下的宽度。
border-radius:左上角水平圆角半径大小 右上角水平圆角半径大小 右下角水平圆角半径大小 左下角水平圆角半径大小/左上角垂直圆角半径大小 右上角垂直圆角半径大小 右下角垂直圆角半径大小 左下角垂直圆角半径大小。
如果忽略垂直圆角值,则等于水平圆角值即此时圆角为 1/4 圆,水平/垂直半径有一个小于等于 0,则这个角是矩形不会是圆的。
border-image:< image > < number > < percentage >
[ stretch | repeat | round ]:拉伸 | 重复 | 平铺 (其中 stretch 是默认值)。
图片裁剪位置< number >:无单位,默认单位 px,支持百分比。
在设置border-image
时实际是将图片进行裁剪形成九个分离区域,然后进行边角设置。
即有了 border-top-image , border-right-image , border-bottom-image , border-left-image, border-top-left-image , border-top-right-image , border-bottom-left-image , border-bottom-right-image 以及中间内容区域。
比如当前边框背景图资源为 81px*81px。
// 边框平铺
div {
border: 20px solid transparent;
width: 300px;
-moz-border-image: url(/i/border.png) 27 round; /* Old Firefox */
-webkit-border-image: url(/i/border.png) 27 round; /* Safari and Chrome */
-o-border-image: url(/i/border.png) 27 round; /* Opera */
border-image: url(/i/border.png) 27 round;
}
// 边框拉伸
div {
border: 20px solid transparent;
width: 300px;
-moz-border-image: url(/i/border.png) 27 stretch; /* Old Firefox */
-webkit-border-image: url(/i/border.png) 27 stretch; /* Safari and Chrome */
-o-border-image: url(/i/border.png) 27 stretch; /* Opera */
border-image: url(/i/border.png) 27 stretch;
}
// 边框重复
div {
border: 20px solid transparent;
width: 300px;
-moz-border-image: url(/i/border.png) 27 repeat; /* Old Firefox */
-webkit-border-image: url(/i/border.png) 27 repeat; /* Safari and Chrome */
-o-border-image: url(/i/border.png) 27 repeat; /* Opera */
border-image: url(/i/border.png) 27 repeat;
}
round 会压缩(或伸展)图片大小使其正好在区域内显示,而 repeat 是不管三七二十一直接重复的,而且是居中重复。
边框图片被切割成 9 部分,以一一对应的关系放到 div 边框的九宫格中,然后再压缩(或拉伸)至边框(border-width 或 border-image-width)的宽度大小。
设置border-image-width
:优先以边框图片宽度。
div {
border-image: url(/i/border.png) 27/10px stretch;
}
Text effects
text-stroke:文字描边属性,宽度+颜色,目前只能实现描边,也无法指定是外描边,内描边还是居中描边,目前指的是剧中描边。
本质上让真实文本的字重削弱了,例如文字在页面上渲染时候,线条粗细大概是 1 像素,这时候我们设置个 1 像素宽的描边,则真实显示粗细岂不是只剩下 0.5 像素,如果真是这样,我们其实可以模拟 font-weight 属性的不同字重效果。但是对于某些字体,由于字重的缺失,font-weight:100 和 font-weight:400 粗细都是一样的,都是正常粗细。
实现外描边可以使用text-shadow
:
.strok-outside {
text-shadow: 0 1px red, 1px 0 red, -1px 0 red, 0 -1px red;
}
多重描边:
text-shadow
属性值可以不断累加,但是 text-stroke
属性却不行,如果想要实现多重描边效果,可以借助伪元素多层叠加模拟。
<p data-text="多重描边">多重描边</p>
p {
-webkit-text-stroke: 1px #fff;
font-size: 40px;
position: relative;
z-index: 0;
}
p::before,
p::after {
content: attr(data-text);
position: absolute;
left: 0;
z-index: -1;
}
p::before {
-webkit-text-stroke: 7px yellow;
}
p::after {
-webkit-text-stroke: 4px red;
}
text-fill-color:文字颜色填充,实现效果基本与color
一致,目前仅webkit
核心浏览器下支持该属性,会覆盖color
属性,主要可实现渐变字体和镂空字体。
渐变字体:
<p class="font1">渐变色字体</p>
.font1 {
font-size: 22px;
background-image: -webkit-linear-gradient(
bottom,
rgb(201, 21, 134),
rgb(20, 11, 255)
);
-webkit-background-clip: text;
-webkit-text-fill-color: transparent;
}
镂空字体(配合text-stroke
):
<p class="font1">我的镂空字体</p>
.font1 {
font-size: 32px;
-webkit-text-fill-color: transparent;
-webkit-text-stroke: 1px #000;
}
word-wrap:文字换行。
经常在渲染文本时由于连续英文字符串过长导致文本溢出(比如 url 链接等),此时可对文本设置强制边界换行。
.word_wrap {
word-wrap: break-word;
}
参考:张鑫旭大神博客