快速上手 Vue - 指令、计算属性、侦听器

文章目录

  • 相关链接
  • 指令
    • 内置指令
    • Class 与 Style 绑定
    • 条件渲染 v-if 与 v-show
    • 列表渲染
    • 事件处理
    • 表单输入绑定
    • 自定义指令
  • 计算属性与侦听器
    • computed
    • watch

相关链接

更多文章和学习资源整理:github
Vue 官方文档:Vue 官方文档

指令

内置指令

指令 描述
v-text 主要用来更新 textContent,可以等同于 JS 的 text 属性。
v-html 双大括号的方式会将数据解释为纯文本,而非 HTML。为了输出真正的HTML,可以用 v-html 指令。它等同于 JS 的 innerHtml 属性。
v-pre 想显示 {{ }} 标签而不进行替换时使用,跳过该元素和它的子元素的编译过程
v-cloak 这个指令保持在元素上直到关联实例结束编译。和 CSS 规则如 [v-cloak] { display: none } 一起用时,这个指令可以隐藏未编译的 Mustache 标签直到实例准备完毕。
v-once v-once关联的实例,只会渲染一次。之后的重新渲染,实例及其所有的子节点将被视为静态内容跳过,这可以用于优化更新性能。
v-if 实现条件渲染,Vue 会根据表达式的值的真假条件来渲染元素。
v-else v-else 是搭配 v-if 使用的,它必须紧跟在 v-if 或者 v-else-if 后面,否则不起作用。
v-else-if v-else-if 充当 v-if 的 else-if 块,可以链式的使用多次。可以更加方便的实现 switch 语句。
v-show 也是用于根据条件展示元素。和 v-if 不同的是,如果 v-if 的值是 false,则这个元素被销毁,不在 dom 中。但是 v-show 的元素会始终被渲染并保存在 dom 中
v-for 遍历数组 / 对象来进行渲染
v-bind 用来动态的绑定一个或者多个特性。没有参数时,可以绑定到一个包含键值对的对象。常用于动态绑定 class 和 style。简写为:【 :】
v-model 用于在表单上创建双向数据绑定。 v-model 会忽略所有表单元素的 value、checked、selected 特性的初始值。因为它选择 Vue 实例数据做为具体的值。
v-on 主要用来监听 dom 事件(或父子组件通信),以便执行一些代码块。表达式可以是一个方法名。简写为:【 @ 】

v-on(绑定事件监听器)
事件修饰符:

  • .stop - 调用 event.stopPropagation()。
  • .prevent - 调用 event.preventDefault()。
  • .capture - 添加事件侦听器时使用 capture 模式。
  • .self - 只当事件是从侦听器绑定的元素本身触发时才触发回调。
  • .{keyCode | keyAlias} - 只当事件是从特定键触发时才触发回调。
  • .native - 监听组件根元素的原生事件。
  • .once - 只触发一次回调。
  • .left - (2.2.0) 只当点击鼠标左键时触发。
  • .right - (2.2.0) 只当点击鼠标右键时触发。
  • .middle - (2.2.0) 只当点击鼠标中键时触发。
  • .passive - (2.3.0) 以 { passive: true } 模式添加侦听器

Class 与 Style 绑定

⑴ 传递一个对象,实现动态切换 class

<div v-bind:class="{ 'active': isActive }">div>

⑵ 与普通的 class 属性共存

<div
  class="static"
  v-bind:class="{ 'active': isActive, 'text-danger': hasError }"
>div>

⑶ 用在组件上时,这些类将被添加到该组件的根元素上面。这个元素上已经存在的类不会被覆盖。
例如,如果你声明了这个组件:

Vue.component('my-component', {
  template: '

Hi

'
})

然后在使用它的时候添加一些 class:

<my-component class="baz boo"></my-component>

HTML 将被渲染为:

<p class="foo bar baz boo">Hip>

⑷ 绑定内联样式

<div v-bind:style="{ color: activeColor, fontSize: fontSize + 'px' }">div>

或者绑定到一个样式对象:

<div v-bind:style="styleObject">div>
data: {
  styleObject: {
    color: 'red',
    fontSize: '13px'
  }
}

条件渲染 v-if 与 v-show

v-if是“真正”的条件渲染,因为它会确保在切换过程中条件块内的事件监听器和子组件适当地被销毁和重建。
v-if也是惰性的:如果在初始渲染时条件为假,则什么也不做——直到条件第一次变为真时,才会开始渲染条件块。
相比之下,v-show就简单得多——不管初始条件是什么,元素总是会被渲染,并且只是简单地基于 CSS 进行切换。
一般来说,v-if有更高的切换开销,而v-show有更高的初始渲染开销。因此,如果需要非常频繁地切换,则使用v-show较好;如果在运行时条件很少改变,则使用v-if较好。

列表渲染

⑴ 只使用 1 个参数

<ul id="example-1">
  <li v-for="item in items">
    {{ item.message }}
  li>
ul>
var example1 = new Vue({
  el: '#example-1',
  data: {
    items: [
      { message: 'Foo' },
      { message: 'Bar' }
    ]
  }
})

⑵ 使用 2 个参数,第二个参数表示当前项的索引

<ul id="example-2">
  <li v-for="(item, index) in items">
    {{ parentMessage }} - {{ index }} - {{ item.message }}
  li>
ul>

⑶ 遍历一个对象的属性,第二个参数(可选)为键名,第三个参数(可选)为索引;遍历对象时,是按 Object.keys() 的结果进行遍历的。

<div v-for="(value, name, index) in object">
  {{ index }}. {{ name }}: {{ value }}
div>
new Vue({
  el: '#v-for-object',
  data: {
    object: {
      title: 'How to do lists in Vue',
      author: 'Jane Doe',
      publishedAt: '2016-04-10'
    }
  }
})

⑷ 需要为每项提供一个唯一的 key 属性,数组下标不行(不合理)

<div v-for="item in items" v-bind:key="item.id">
  
div>

v-for 也可以接受整数。在这种情况下,它会把模板重复对应次数

<div>
  <span v-for="n in 10">{{ n }} span>
div>

⑹ 数组更新检测
Vue 将被侦听的数组的变异方法进行了包裹,所以它们也将会触发视图更新。这些被包裹过的方法包括:

  • push()
  • pop()
  • shift()
  • unshift()
  • splice()
  • sort()
  • reverse()

Vue不能检测以下数组的变动:

  1. 当你利用索引直接设置一个数组项时,例如:vm.items[indexOfItem] = newValue
  2. 当你修改数组的长度时,例如:vm.items.length = newLength
var vm = new Vue({
  data: {
    items: ['a', 'b', 'c']
  }
})
vm.items[1] = 'x' // 不是响应性的
vm.items.length = 2 // 不是响应性的

为了解决第一类问题,以下两种方式都可以实现和vm.items[indexOfItem] = newValue相同的效果,同时也将在响应式系统内触发状态更新:

// Vue.set
Vue.set(vm.items, indexOfItem, newValue)
// Array.prototype.splice
vm.items.splice(indexOfItem, 1, newValue)

你也可以使用 vm.$set 实例方法,该方法是全局方法 Vue.set 的一个别名:

vm.$set(vm.items, indexOfItem, newValue)

为了解决第二类问题,你可以使用 splice

vm.items.splice(newLength)

事件处理

事件修饰符

  • .stop - 调用 event.stopPropagation()。
  • .prevent - 调用 event.preventDefault()。
  • .capture - 添加事件侦听器时使用 capture 模式。
  • .self - 只当事件是从侦听器绑定的元素本身触发时才触发回调。
  • .{keyCode | keyAlias} - 只当事件是从特定键触发时才触发回调。
  • .native - 监听组件根元素的原生事件。
  • .once - 只触发一次回调。
  • .left - (2.2.0) 只当点击鼠标左键时触发。
  • .right - (2.2.0) 只当点击鼠标右键时触发。
  • .middle - (2.2.0) 只当点击鼠标中键时触发。
  • .passive - (2.3.0) 对应于 addEventListener 中的 passive 选项

例如:
@click.stop.prevent:禁止事件冒泡和预设行为,移动端下拉事件经常使用
@click.prevent:不处理任何的点击事件,可以给 Toast 的蒙版添加该行为
@keyup.enter.exact 或者 @keyup.13.exact:keyup 是按下按键抬起后触发 exact 精确要求回车, 不加的话按 shift+enter 也会触发


<a v-on:click.stop="doThis">a>


<form v-on:submit.prevent="onSubmit">form>


<a v-on:click.stop.prevent="doThat">a>


<form v-on:submit.prevent>form>



<div v-on:click.capture="doThis">...div>



<div v-on:click.self="doThat">...div>

v-on 用在普通元素上时,只能监听原生 DOM 事件。用在自定义元素组件上时,也可以监听子组件触发的自定义事件

表单输入绑定

v-model

<input v-model="searchText">
等价于:
<input
  v-bind:value="searchText"
  v-on:input="searchText = $event.target.value"
>

v-model在内部为不同的输入元素使用不同的属性并抛出不同的事件:

  • text 和 textarea 元素使用value属性和input事件;
  • checkbox 和 radio 使用checked属性和change事件;
  • select 字段将value作为 prop 并将change作为事件。

v-model 会忽略所有表单元素的 value、checked、selected 特性的初始值而总是将 Vue 实例的数据作为数据来源。你应该通过 JavaScript 在组件的 data 选项中声明初始值。


当用在组件上时,v-model则会这样:

<custom-input
  v-bind:value="searchText"
  v-on:input="searchText = $event"
>custom-input>

为了让它正常工作,这个组件内的 必须:
• 将其 value 特性绑定到一个名叫 value 的 prop 上
• 在其 input 事件被触发时,将新的值通过自定义的 input 事件抛出

Vue.component('custom-input', {
  props: ['value'],
  template: `
    <input
      v-bind:value="value"
      v-on:input="$emit('input', $event.target.value)"
    >
  `
})

现在 v-model 就应该可以在这个组件上完美地工作起来了:

<custom-input v-model="searchText">custom-input>

自定义指令

// 注册一个全局自定义指令 `v-focus`
Vue.directive('focus', {
  // 当被绑定的元素插入到 DOM 中时……
  inserted: function (el) {
    // 聚焦元素
    el.focus()
  }
})

如果想注册局部指令,组件中也接受一个directives的选项:

directives: {
  focus: {
    // 指令的定义
    inserted: function (el) {
      el.focus()
    }
  }
}

然后你可以在模板中任何元素上使用新的v-focus属性,如下:

<input v-focus>

计算属性与侦听器

computed

对于模板中的复杂逻辑,应该将其设置为计算属性

<div id="example">
  <p>Original message: "{{ message }}"</p>
  <p>Computed reversed message: "{{ reversedMessage }}"</p>
</div>
var vm = new Vue({
  el: '#example',
  data: {
    message: 'Hello'
  },
  computed: {
    // 计算属性的 getter
    reversedMessage: function () {
      // `this` 指向 vm 实例
      return this.message.split('').reverse().join('')
    }
  }
})

当 vm.message 发生改变时,vm.reversedMessage 会自动更新。
调用方法也可以实现同样的效果:

<p>Reversed message: "{{ reversedMessage() }}"p>
// 在组件中
methods: {
  reversedMessage: function () {
    return this.message.split('').reverse().join('')
  }
}

区别是:计算属性是基于它们的响应式依赖进行缓存的。只在相关响应式依赖发生改变时它们才会重新求值。这就意味着只要message还没有发生改变,多次访问reversedMessage计算属性会立即返回之前的计算结果,而不必再次执行函数。

watch

侦听器 watch 是一种通用的用于观察和响应 Vue 实例上的数据变动的方式,使用方式如下:

<div id="demo">{{ fullName }}div>
var vm = new Vue({
  el: '#demo',
  data: {
    firstName: 'Foo',
  },
  watch: {
    // 监听的属性和其发生变化后触发的回调
    firstName: function (val) {
      this.fullName = val + ' ' + this.lastName
    }
  }
})

你可能感兴趣的:(vue,前端,Vue,指令,计算属性)