1. 程式人生 > >vue.js---元件的基礎

vue.js---元件的基礎

元件的基礎:
1、示例:

// 定義一個名為 button-counter 的新元件
Vue.component('button-counter', {
  data: function () {
    return {
      count: 0
    }
  },
  template: '<button v-on:click="count++">You clicked me {{ count }} times.</button>'
})

<div id="components-demo">
  <button-counter></button-counter>
</div>

new
Vue({ el: '#components-demo' })

data 必須是一個函式,如果不是一個函式,而是一個變數的話,如果有元件複用,那麼修改一個值其他元件的值也會被修改,這樣是不好的,所以data必須是一個函式

為了能在模板中使用,這些元件必須先註冊以便 Vue 能夠識別。這裡有兩種元件的註冊型別:全域性註冊和區域性註冊。至此,我們的元件都只是通過 Vue.component 全域性註冊的:

通過 Prop 向子元件傳遞資料:

Vue.component('blog-post', {
  props: ['title'],
  template: '<h3>{{ title }}</h3>'
}) new Vue({ el: '#blog-post-demo', data: { posts: [ { id: 1, title: 'My journey with Vue' }, { id: 2, title: 'Blogging with Vue' }, { id: 3, title: 'Why Vue is so fun' } ] } }) <blog-post v-for="post in posts" v-bind:key="post.id" v-bind:title="post.title"
></blog-post>

單個根元素

Vue.component('blog-post', {
  props: ['post'],
  template: `
    <div class="blog-post">
      <h3>{{ post.title }}</h3>
      <div v-html="post.content"></div>
    </div>
  `
})

<blog-post
  v-for="post in posts"
  v-bind:key="post.id"
  v-bind:post="post"
></blog-post>

通過事件向父級元件傳送訊息

new Vue({
  el: '#blog-posts-events-demo',
  data: {
    posts: [/* ... */],
    postFontSize: 1
  }
})

<div id="blog-posts-events-demo">
  <div :style="{ fontSize: postFontSize + 'em' }">
    <blog-post
      v-for="post in posts"
      v-bind:key="post.id"
      v-bind:post="post" 
       v-on:enlarge-text="postFontSize += 0.1"
    ></blog-post>
  </div>
</div>

Vue.component('blog-post', {
  props: ['post'],
  template: `
    <div class="blog-post">
      <h3>{{ post.title }}</h3>
      <button v-on:click="$emit('enlarge-text')">
      Enlarge text
    </button>
      <div v-html="post.content"></div>
    </div>
  `
})

也可以使用事件丟擲一個值:

<button v-on:click="$emit('enlarge-text', 0.1)">
  Enlarge text
</button>

<blog-post
  ...
  v-on:enlarge-text="postFontSize += $event"
></blog-post>

也可以使用事件處理函式:

<blog-post
  ...
  v-on:enlarge-text="onEnlargeText"
></blog-post>

methods: {
  onEnlargeText: function (enlargeAmount) {
    this.postFontSize += enlargeAmount
  }
}

在元件中使用v-model

<input v-model="searchText">
等價於
<input
  v-bind:value="searchText"
  v-on:input="searchText = $event.target.value"
>
在元件中使用v-model:
一個元件上的 v-model 預設會利用名為 value 的 prop 和名為 input 的事件
Vue.component('custom-input', {
  props: ['value'],
  template: `
    <input
      v-bind:value="value"
      v-on:input="$emit('input', $event.target.value)"
    >
  `
})

<custom-input v-model="searchText"></custom-input>
但是像單選框、複選框等型別的輸入控制元件可能會將 value 特性用於不同的目的。model 選項可以用來避免這樣的衝突:

Vue.component('base-checkbox', {
  model: {
    prop: 'checked',
    event: 'change'
  },
  props: {
    checked: Boolean
  },
  template: `
    <input
      type="checkbox"
      v-bind:checked="checked"
      v-on:change="$emit('change', $event.target.checked)"
    >
  `
})

現在在這個元件上使用 v-model 的時候:

<base-checkbox v-model="lovingVue"></base-checkbox>

這裡的 lovingVue 的值將會傳入這個名為 checked 的 prop。同時當 <base-checkbox> 觸發一個 change 事件並附帶一個新的值的時候,這個 lovingVue 的屬性將會被更新。

解析 DOM 模板時的注意事項

有些 HTML 元素,諸如 <ul><ol><table><select>,對於哪些元素可以出現在其內部是有嚴格限制的。而有些元素,諸如 <li><tr><option>,只能出現在其它某些特定的元素內部。

這會導致我們使用這些有約束條件的元素時遇到一些問題。例如:

<table>
  <blog-post-row></blog-post-row>
</table>

這個自定義元件 <blog-post-row> 會被作為無效的內容提升到外部,並導致最終渲染結果出錯。幸好這個特殊的 is 特性給了我們一個變通的辦法:

<table>
  <tr is="blog-post-row"></tr>
</table>

需要注意的是如果我們從以下來源使用模板的話,這條限制是不存在的:

    字串 (例如:template: '...')
    單檔案元件 (.vue)
    <script type="text/x-template">

到這裡,你需要了解的解析 DOM 模板時的注意事項——實際上也是 Vue 的全部必要內容,大概就是這些了。恭喜你!接下來還有很多東西要去學習,不過首先,我們推薦你先休息一下,試用一下 Vue,自己隨意做些好玩的東西。

如果你感覺已經掌握了這些知識,我們推薦你再回來把完整的元件指南,包括側邊欄中元件深入章節的所有頁面讀完。