Vue 模板语法——属性绑定(3)

313 阅读2分钟

小知识,大挑战!本文正在参与“程序员必备小知识”创作活动。

1. 绑定 style 属性

有时候我们需要根据数据来动态决定某些内联样式(比如某段文字的的颜色大小等等),这时就可以使用 v-bind:style:style) 来绑定 CSS 内联样式

CSS 属性名可以用 驼峰式(camelCase短横线分隔(kebab-case,记得用引号包裹起来哦) 来命名。

绑定 style 有两种方式:对象或数组。

1.1 对象语法

<template id="my-app">
  <!-- 对象格式:{ CSSPropertyName: CSSPropertyValue }" -->
  
  <!-- 1. 基本使用:传入一个对象,对象中的内容都是静态的(确定的) -->
  <div :style="{ color: 'red', fontSize: '30px', 'background-color': 'skyblue' }">{{ message }}</div>
  <!-- 2. 变量数据:传入一个对象,对象中的值来自于 data -->
  <div :style="{ color: activeColor, fontSize: fontSize + 'px', 'background-color': 'skyblue' }">
    {{ message }}
  </div>
  <!-- 3. 对象数据:直接在 data 中定义好对象,然后在这里使用(直接绑定到一个样式对象通常更好,这会让模板更清晰) -->
  <div :style="styleObj">{{ message }}</div>
  <!-- 4. 也可以调用返回样式对象的方法,再绑定这个样式对象(使用方法的情况较少,更多的是使用计算属性) -->
  <div :style="getStyleObj()">嘻嘻嘻</div>
  <!-- 5. 也可以绑定返回样式对象的计算属性(常用,后面讲计算属性时再说) -->

  <!-- CSS property 名可以用驼峰式命名,也可以用短横线分隔式命名(但要用引号包裹), -->
  <!-- 注意:CSS property 名后面对应的值是一个表达式(表达式中如果使用了不存在的数据属性,该样式不会生效) -->
  <div :style="{ color: 'red', fontSize: 20 + 'px', 'font-weight': 700 }">哈哈哈</div>
  <!-- red 不会被当作字符串,而是会被当成数据属性,由于不存在该数据属性,所以此样式不会生效 -->
  <!-- <div :style="{ color: red }">哈哈哈</div> -->

</template>

<body> 中的完整代码:

<div id="app"></div>

<template id="my-app">
  <!-- 对象格式:{ CSSPropertyName: CSSPropertyValue }" -->

  <!-- 1. 基本使用:传入一个对象,对象中的内容都是静态的(确定的) -->
  <div :style="{ color: 'red', fontSize: '30px', 'background-color': 'skyblue' }">{{ message }}</div>
  <!-- 2. 变量数据:传入一个对象,对象中的值来自于 data -->
  <div :style="{ color: activeColor, fontSize: fontSize + 'px', 'background-color': 'skyblue' }">
    {{ message }}
  </div>
  <!-- 3. 对象数据:直接在 data 中定义好对象,然后在这里使用(直接绑定到一个样式对象通常更好,这会让模板更清晰) -->
  <div :style="styleObj">{{ message }}</div>
  <!-- 4. 也可以调用返回样式对象的方法,再绑定这个样式对象(使用方法的情况较少,更多的是使用计算属性) -->
  <div :style="getStyleObj()">嘻嘻嘻</div>
  <!-- 5. 也可以绑定返回样式对象的计算属性(常用,后面讲计算属性时再说) -->

  <!-- CSS property 名可以用驼峰式命名,也可以用短横线分隔式命名(但要用引号包裹), -->
  <!-- 注意:CSS property 名后面对应的值是一个表达式(表达式中如果使用了不存在的数据属性,该样式不会生效) -->
  <div :style="{ color: 'red', fontSize: 20 + 'px', 'font-weight': 700 }">哈哈哈</div>
  <!-- red 不会被当作字符串,而是会被当成数据属性,由于不存在该数据属性,所以此样式不会生效 -->
  <!-- <div :style="{ color: red }">哈哈哈</div> -->

</template>

<script src="./js/vue.js"></script>
<script>
  const App = {
    data() {
      return {
        message: '你好啊',
        activeColor: 'red',
        fontSize: 30,
        styleObj: {
          color: 'red',
          // 可以用短横线分隔式命名,但开发中我们在对象中编写 key 时更习惯于使用驼峰式命名
          'font-size': '30px',
          backgroundColor: 'skyblue'
        }
      }
    },
    methods: {
      getStyleObj() {
        return {
          color: 'red',
          // 可以用短横线分隔式命名,但开发中我们在对象中编写 key 时更习惯于使用驼峰式命名
          'font-size': '30px',
          backgroundColor: 'skyblue'
        };
      }
    },
    template: '#my-app'
  };

  Vue.createApp(App).mount('#app');
</script>

1.2 数组语法

当我们需要将多个样式对象应用到同一个元素上时,可以使用 :style 的数组语法:

<div :style="[style1Obj, style2Obj]">{{ message }}</div>

<body> 中的完整代码:

<div id="app"></div>

<template id="my-app">
  <!-- 
    数组格式:
      [
        {
          CSSPropertyName1: CSSPropertyValue1,
          CSSPropertyName2: CSSPropertyValue2,
          ...
        },
        {
          CSSPropertyName3: CSSPropertyValue3,
          CSSPropertyName4: CSSPropertyValue4,
          ...
        },
			  ...
      ]
  -->

  <div :style="[style1Obj, style2Obj]">{{ message }}</div>
</template>

<script src="./js/vue.js"></script>
<script>
  const App = {
    data() {
      return {
        message: '你好啊',
        style1Obj: {
          color: 'red',
          fontWeight: 'bold'
        },
        style2Obj: {
          textDecoration: 'underline',
          color: 'green'
        }
      }
    },
    template: '#my-app'
  };

  Vue.createApp(App).mount('#app');
</script>

数组中的多个样式对象会进行合并,如果这些对象中存在相同的 CSS 属性,那么最终会使用顺序最靠后的对象中的值(如上面的 color,最后生效的值是 green)。

2. 动态绑定属性名

在某些情况下,HTML 属性的名称可能也不是固定的:

  • 前面我们绑定的 srchrefclassstyle 属性,属性名称都是固定的;
  • 如果属性名称不是固定的,我们可以使用 :[属性名]="值" 的格式来定义;
  • 这种绑定方式,我们称之为动态属性名的绑定

示例:

<!-- 属性的名称是动态的 -->
<div :[name]="value"></div>
data() {
  return {
    name: 'abc',
    value: '你好啊'
  }
}

渲染的结果为:

<div abc="你好啊"></div>

3. 绑定一个全是属性的对象

如果我们希望将一个对象的所有属性,绑定到元素上的所有属性,就可以使用 v-bind="对象" 的格式来实现。

示例:

<!-- 想要的效果: -->
<div name="coderzhj" age="20" height="1.88"></div>
<!-- 用 v-bind 指令实现该效果的方式: -->
<div v-bind="info"></div>
<!-- 这里也可以使用语法糖,但阅读性有点差,不推荐这样写 -->
<div :="info"></div>
data() {
  return {
    info: {
      name: 'coderzhj',
      age: 20,
      height: 1.88
    }
  }
}

上述示例中的 info 对象会被拆解成 div 的各个属性。