vue中$attrs的使用
阿新 • • 發佈:2021-07-20
功能:
- 專案中有多層元件傳參可以使用$attrs,可以使程式碼更加美觀,更加簡潔,維護程式碼的時候更方便。如果使用普通的父子元件傳參prop和$emit,$on會很繁瑣;如果使用vuex會大材小用,只是在這幾個元件中使用,沒必要使用vuex;使用事件匯流排eventBus,使用不恰當的話,有可能會出現事件多次執行。
- 如果給子元件傳遞非 prop 屬性,那麼這些屬性將繫結在子元件的根元素上。
- 如果子元件中不想繼承父元件傳入的非 prop 屬性,可以使用inheritAttrs: false 禁用繼承,然後通過 v-bind="$attrs" 把外部傳入的非 prop 屬性設定給希望的標籤上。inheritAttrs: false 是不會影響 style 和 class 的繫結。
- 多級元件傳值時,呼叫目標元件繫結$attrs,可直接獲取根元件所傳遞引數,而不用每一級元件逐層傳遞。
以下是$attrs
的使用示例(父元件的列表行資料傳遞給孫子元件展示)
1.父元件(Father.vue),給子元件關聯資料,子元件如果不用props接收,那麼這些資料就作為普通的HTML特性應用在子元件的根元素上
<template> <div> <el-table :data='list'> <el-table-column prop="name" label="姓名"></el-table-column> <el-table-column prop="study" label="學習科目"></el-table-column> <el-table-column label="操作"> <template slot-scope="scope"> <el-button @click='transmitClick(scope.row)'>傳遞</el-button> </template> </el-table-column> </el-table> <!-- 兒子元件 --> <ChildView :is-show="isOpen" :row="row" :abc="123"></ChildView> </div> </template> <script> import ChildView from'./Child.vue' export default { components: { ChildView }, data() { return { isOpen: false, row: {}, list: [ { name: '王麗', study: 'Java' }, { name: '李克', study: 'Python' } ] } }, methods: { // 傳遞事件 transmitClick(row) { this.isOpen = true; this.row = row } } } </script>
2.兒子元件(Child.vue),中間層,作為父元件和孫子元件的傳遞中介,在兒子元件中給孫子元件新增v-bind="$attrs"
,這樣孫子元件才能接收到資料。
<template> <div class='child-view'> <p>兒子元件</p> <GrandChild v-bind="$attrs"></GrandChild> </div> </template> <script> import GrandChild from './GrandChild.vue' export default { // 繼承所有父元件的內容 inheritAttrs: true, components: { GrandChild }, data() { return {} } } </script> <style> .child-view { margin: 20px; border: 2px solid red; padding: 20px; } </style>
3.孫子元件(GrandChild.vue),在孫子元件中一定要使用props接收從父元件傳遞過來的資料
<template> <div class='grand-child-view'> <p>孫子元件</p> <p>傳給孫子元件的資料:{{row.name}} {{row.name !== undefined? '學習' : ''}} {{row.study}}</p> </div> </template> <script> export default { // 不想繼承所有父元件的內容,同時也不在元件根元素dom上顯示屬性 inheritAttrs: false, // 在本元件中需要接收從父元件傳遞過來的資料,注意props裡的引數名稱不能改變,必須和父元件傳遞過來的是一樣的 props: { isShow: { type: Boolean, dedault: false }, row: { type: Object, dedault: () => { } } } } </script> <style> .grand-child-view { border: 2px solid green; padding: 20px; margin: 20px; } </style>
結果:
在上面提過,如果給子元件傳遞的資料,子元件不使用props接收,那麼這些資料將作為子元件的特性,這些特性繫結在元件的HTML根元素上,在vue2.40版本之後,可以通過inheritAttrs = false 來控制這些特性是否顯示在dom元素上 如:案例中父元件給子元件傳遞的row和isShow,子元件沒有使用props接收,這個2個數據直接作為HTML的特殊屬性。子元件使用inheritAttrs = true,那麼特性顯示在dom上,如果設定為false,那麼特性不顯示在dom上。