跳转至

CSS高级功能

自定义属性

CSS 提供的属性(比如font-weightline-height)都是标准给定的,但是 CSS 也允许用户自定义属性,这又称为“CSS 变量”。

自定义属性跟普通属性一样,也是定义在某个选择器里面,而且只对该选择器有效。因此自定义属性所在区块,相当于变量的作用域。

:root选择器之中,可以设置全局的自定义属性。

:root {
  --base: #ffc600;
  --spacing: 10px;
  --blur: 10px;
}

变量也可以在行内定义。

<html style = "--color: red;">

所有自定义属性都必须以两个连词线开头,并且大小写敏感。

使用时,通过var()函数取出变量。

img {
  padding: var(--spacing);
  background: var(--base);
  -webkit-filter: blur(var(--blur));
  filter: blur(var(--blur));
}

var()函数接受第二个参数,指定默认值。如果某个自定义属性没有设置,默认值就会生效。

width: var(--custom-width, 20%);

下面是另一个例子。

foo {
  padding: var(--gutter, 10px 0 0 5px);
}

如果默认值包含逗号,那么var()会将第一个逗号后面的所有值,当作默认值。

.someElement {
  font-family: var(--main-font, "lucida grande" , tahoma, Arial);
}

上面代码中,--main-font的默认值是"lucida grande" , tahoma, Arial

var()内部还可以使用var()

.someElement {
  background-color: var(--first-color, var(--second-color, white));
}

上面代码中,如果没有设置--first-color,默认值var(--second-color, white)就会生效。如果--second-color也没有设置,那么white就会生效。

自定义属性可以是全局的,也可以是局部的。在:root选择器里面定义的,就是全局变量,可以在任何其他选择器里面读取。而在其他选择器里面定义,就是局部变量,只能在该选择器里面读取。

下面代码中,局部变量可以覆盖全局变量。

:root { --text-color: green; }
div { --text-color: blue; }
.error { --text-color: red; }

* {
  color: var(--text-color);
}

上面代码中,一般文字是绿色,div元素的文字是蓝色,error类的文字是红色。

定义变量的时候,也可以读取其他变量。

:root {
  --brand-color: red;
  --header-text-color: var(--brand-color);
}

变量也可以与calc函数结合使用。

:root {
  --container-width: 1000px;
  max-width: calc(var(--container-width) / 2);
}

变量不包含单位时,不能直接添加单位。

/* 无效 */
.quote {
  --t-padding: 20;
  padding-top: var(--t-padding)px;
}

/* 有效 */
.quote {
  --t-padding: 20;
  padding-top: calc(var(--t-padding) * 1px);
}

JavaScript 可以操作这些变量。

element.style.setProperty('--my-color', 'rebeccapurple');
element.style.getPropertyValue('--my-color');
// "rebeccapurple"
element.style.removeProperty('--my-color');

下面是例子。

// 取得变量值
var styles = window.getComputedStyle(document.documentElement);
var bgValue = String(styles.getPropertyValue('--background')).trim();

// 设置变量值
document.documentElement.style.setProperty('--background', 'black');
// 另一种写法
document.documentElement.style.setProperty('--h-color', 'var(--p-color)');

下面是一个监听事件的例子。

const docStyle = document.documentElement.style;

document.addEventListener('mousemove', (e) => {
  docStyle.setProperty('--mouse-x', e.clientX);
  docStyle.setProperty('--mouse-y', e.clientY);
});

下面是一个使用CSS变量的例子,只要<input>的值发生变化,样式就会随之发生变化。

// get the inputs
const inputs = [].slice.call(document.querySelectorAll('.controls input'));

// listen for changes
inputs.forEach(input => input.addEventListener('change', handleUpdate));
inputs.forEach(input => input.addEventListener('mousemove', handleUpdate));

function handleUpdate(e) {
  // append 'px' to the end of spacing and blur variables
  const suffix = (this.id === 'base' ? '' : 'px');
  document.documentElement.style.setProperty(`--${this.id}`, this.value + suffix);
}

参考链接

supports

supports命令用来判断浏览器是否支持某项CSS功能。

@supports not (display: grid) {
  // 不支持网格布局
  // 老式浏览器代码
}
@supports (display: grid) {
  // 支持网格布局
  // 新式浏览器代码
}

另一个例子。

@supports (object-fit: cover) {
  img {
    object-fit: cover;
  }
  div {
    width: auto;
    background: green;
   // some other complex code for the fancy new layout
  }
}

initial-letter

initial-letter决定首字母的下沉样式。

/* 默认值 */
initial-letter: normal;

/* 占据1.5行高度 */
initial-letter: 1.5;

/* 占据3行高度 */
initial-letter: 3.0;

/* 占据3行高度,下沉2行高度 */
initial-letter: 3.0 2;

滤镜

网页的灰度显示。

html {
  -webkit-filter: grayscale(100%);
  filter: grayscale(100%);
}

CSS Shape

shape-outside属性使得行内(inline)的内容,围绕outside指定的曲线排列。

shape-margin属性指定shape-outside与内容之间的margin

.circle {
  width: 250px;
  height: 250px;
  background-color: #40a977;
  border-radius: 50%;
  float: left;
  -webkit-shape-outside: circle();
  shape-outside: circle();
}

circle函数可以使用circle(r at x y)这样的形式,定义半径和圆心的坐标。注意,这里的坐标是相对于原始形状,而不是相对于父容器。

其他形状的函数。

  • ellipse()
  • polygon()

参考链接