Vue 元件複用多次自定義引數操作
場景:
當專案中多處出現相同的模組時,此時的正常考慮是將其做成公共組建,通過傳參不同,實現多處複用
具體:
背景:專案使用的技術是VUE+ElementUI
此處,多處出現的模組是select選擇框,封裝成元件後,傳給它option的值,程式碼如下:
<!--元件檔案 比如說這個元件叫 vSelect 下面會用--> <template> <el-select @change="handleChange" v-model="value" :placeholder="請選擇"> <el-option v-for="(item,index) in options" :key="index" :label="item.label" :value="item.value"> </el-option> </el-select> </template> <script> export default { data() { return { value: '',} },props:['options'],methods: { handleChange(value) { this.$emit('my-event',value); } },} </script>
使用時只需把檔案import進來,程式碼如下:
<template> <vSelect :options="options" @my-event="select"></vSelect> </template> <script> import vSelect from '檔案路徑' export default { data() { return { options: [ { value:0,label:'選項一' },{ value:1,label:'選項二' },],} },components: { vSelect },methods: { select(value) { console.log(value) } },} </script>
以上的話便可以實現一個元件的簡單呼叫,選擇後的值會從子元件傳到父元件
問題:
多處使用同一個元件時,會代表不同的選項,拿到的值也需要做不同的處理,正常也可以通過寫多個方法來實現對取得的值的不同處理,但是這種方法不夠靈活。
解決:
此時自然而然想到的一種解決方法就是給上面的select函式再增加一個引數,根據引數不同進行不同的處理
但是真正實施起來卻發現會出現很多問題。
其實解決方法很簡單,就是一開始沒轉過來彎,還是花了一些時間,最終的解決方案就是使用回撥函式:
<vSelect :options="options" @my-event="val=>select(val,param)"></vSelect> select(value,param) { console.log(value,param) }
回過頭來看,真的覺的這個壓根都不能算作一個問題,就當記錄一下作為Vue元件使用的初級教程吧,希望能夠幫助到一些人。
補充知識:VUE之元件(插槽slot與可複用元件)
插槽slot
當子元件部分內容是通過父元件傳遞DOM進行顯示時,可以不用父元件props傳值的比較挫的語法,Vue中提供了一種新型語法:插槽slot。
廢話不多說看程式碼:
<!-- html程式碼 --> <div id="app"> <my-blog> <h2>格林童話</h2> <cite>格林兄弟</cite> <p>白雪公主和七個小矮人</p> </my-blog> </div> // vue程式碼 Vue.component('my-blog',{ template:` <div> <slot></slot> <span>惡毒的皇后</span> </div>` }) var app=new Vue({ el:"#app",})
命名由來:
這種語法看起來像是用子元件直接往裡直接插DOM內容,所以稱之為插槽。
小結:
1、插槽(Slot)是Vue提出來的一個概念,正如名字一樣,插槽用於決定將所攜帶的內容,插入到指定的某個位置,從而使模板分塊,具有模組化的特質和更大的重用性;
2、插槽顯不顯示、怎樣顯示是由父元件來控制的,而插槽在哪裡顯示就由子元件來進行控制
插槽分類有很多種,本節將一一介紹
(1)單個插槽/預設插槽
(2)具名插槽
(3)作用域插槽
(4)解構插槽
插槽分類一:單個插槽(備胎插槽)
出現緣由:
最初在 標籤中的任何內容都被視為備用內容。
備用內容在子元件的作用域內編譯,並且只有在宿主元素為空,且沒有要插入的內容時才顯示備用內容。
插槽分類一:單個插槽(備胎)
(1)宿主元素不為空時,顯示宿主元素裡內容,不顯示備用內容
<!-- html程式碼 --> <div id="app"> <my-blog></my-blog> </div> // vue程式碼 Vue.component('my-blog',{ template:` <div> <slot>備用內容</slot> <span>惡毒的皇后</span> </div>` }) var app=new Vue({ el:"#app",})
注意:此時上面沒有內容的情況下會自動填上預設的內容
官方文件描述:
Vue 實現了一套內容分發的 API,將 元素作為承載分發內容的出口
插槽內可以包含任何模板程式碼,包括 HTML模板程式碼,甚至可以是其它的元件。
通俗理解:
沒有插槽的情況下在元件標籤內寫一些內容是不起任何作用的,當在元件中聲明瞭插槽元素後,在元件元素內寫的內容就會跑到它這裡了,即插槽此時充當承載分發內容的出口!
具名插槽
首先看個案例,結合案例瞭解下具名插槽的概念
(1)在子元件中定義了三個slot標籤,其中有兩個分別添加了name屬性header和footer。即通過給slot新增name屬性,來指定當前slot的名字
<!-- html程式碼 --> <div id="app"> <my-blog> <h2 slot="header">格林童話</h2> <cite>格林兄弟</cite> <p slot="footer">白雪公主和七個小矮人</p> </my-blog> </div> // vue程式碼 Vue.component('my-blog',{ template:` <div> <slot name="header"></slot> <span>惡毒的皇后</span> <slot></slot> <slot name="footer"></slot> </div>` }) var app=new Vue({ el:"#app",})
具名插槽小結
(1)具名插槽其實就是在父元件中新增一個 slot=‘自定義名字' 的屬性,然後在子元件中的 裡面新增 name=‘自定義名字' 即可
(2)如果父元件中有一部分沒有新增 slot 屬性,則此處就是預設的插槽,在子元件中的 直接就是使用的父元件的預設插槽部分
(3)如果沒有預設插槽,這些找不到匹配的內容片段將被拋棄。
作用域插槽slot
簡介:
作用域插槽為Vue2.1.0版本新增,是一種特殊型別的插槽,用作一個 (能被傳遞資料的) 可重用模板,來代替已經渲染好的元素。
父元件模板的所有東西都會在父級作用域內編譯;子元件模板的所有東西都會在子級作用域內編譯。
不過,我們可以在父元件中使用 slot-scope 特性從子元件獲取資料。前提是需要在子元件中使用 :data=data 先傳遞 data 的資料。
作用域插槽案例:
<!-- html程式碼 --> <div id="app"> <!-- 利用solt-scope獲取資料 --> <my-blog> <template slot-scope="props"> {{props.data}} </template> </my-blog> </div> // vue程式碼 // 1.子元件傳遞資料 Vue.component('my-blog',{ template: `<div> <slot :data="text"></slot> </div>`,data() { return { text: '喜歡福安' } } }) var app = new Vue({ el: "#app",})
注意:
(1)在父級中,具有特殊特性 slot-scope 的 元素必須存在,表示它是作用域插槽的模板(在 2.5.0+,slot-scope 能被用在任意元素或元件中而不再侷限於 )。
(2)slot-scope 的值將被用作一個臨時變數名,此變數接收從子元件傳遞過來的 prop 物件
(3)在子元件中,只需將資料傳遞到插槽,就像你將 prop 傳遞給元件一樣,接下來父元件中使用 slot-scope 特性從子元件獲取資料
案例:blog子元件可能在很多地方呼叫,希望在不同地方呼叫blog元件時
但是:注意這裡要求列表的迴圈和樣式不是由子元件決定,而是外部決定的,修改程式碼如下
<!-- html程式碼 --> <div id="app"> <!-- 利用solt-scope獲取資料 --> <my-blog> <template slot-scope="props"> <h1>{{props.data}}</h1> </template> </my-blog> <my-blog> <template slot-scope="props"> <h4>{{props.data}}</h4> </template> </my-blog> </div> // vue程式碼 // 1.子元件傳遞資料 Vue.component('my-blog',{ template: ` <div> <ul> <li v-for="text of texts"> <slot :data="text"></slot> </li> </ul> </div>`,data() { return { texts: ["汪汪隊","彩虹寶寶","天線寶寶","蘇菲亞","大頭兒子小頭爸爸","熊出沒"] } } }) var app = new Vue({ el: "#app",})
條件判斷渲染
到目前為止,便可以在元素上隨便操作了
例如:當名字長度等於3的時候,在前面加個“你好”標誌
程式碼如下
<!-- html程式碼 --> <div id="app"> <!-- 利用solt-scope獲取資料 --> <my-blog> <template slot-scope="props"> <h1 v-if="props.data.length==3">新推薦--{{props.data}}</h1> <h1 v-else>{{props.data}}</h1> </template> </my-blog> </div> // vue程式碼 // 1.子元件傳遞資料 Vue.component('my-blog',})
作用域插槽slot-scrop新語法
版本:自 2.6.0 起有所更新,已廢棄使用 slot-scope 語法,開始使用v-slot進行替代,如下所示
<!-- html程式碼 --> <div id="app"> <!-- 利用solt-scope獲取資料 --> <my-blog> <template v-slot="props"> <h1 v-if="props.data.length==3">新推薦--{{props.data}}</h1> <h1 v-else>{{props.data}}</h1> </template> </my-blog> </div>
解構插槽:
v-slot 的值實際上可以是任何能夠作為函式定義中的引數的 JS表示式。所以在支援的環境下 (單檔案元件或現代瀏覽器),你也可以使用 ES2015 解構來傳入具體的插槽 prop,如下:
<!-- html程式碼 --> <div id="app"> <!-- 利用solt-scope獲取資料 --> <my-blog> <template v-slot="{data}"> <h1 v-if="data.length==3">新推薦--{{data}}</h1> <h1 v-else>{{data}}</h1> </template> </my-blog> </div> // vue程式碼 // 1.子元件傳遞資料 Vue.component('my-blog',})
作用域插槽slot-scrop新語法
你甚至可以定義後備內容,用於插槽 prop 是 undefined 的情形
<!-- html程式碼 --> <div id="app"> <!-- 利用solt-scope獲取資料 --> <my-blog> <template v-slot="{data='這部電視禁播了'}"> <h1 v-if="data.length==3">新推薦--{{data}}</h1> <h1 v-else>{{data}}</h1> </template> </my-blog> </div> // vue程式碼 // 1.子元件傳遞資料 Vue.component('my-blog',undefined,})
編寫可複用元件注意事項:
在編寫元件時,最好考慮好以後是否要進行復用。一次性元件間有緊密的耦合沒關係,但是可複用元件應當定義一個清晰的公開介面,同時也不要對其使用的外層資料作出任何假設。
Vue 元件的 API 來自三部分——prop、事件和插槽:
1、Prop 允許外部環境傳遞資料給元件;
2、事件允許從元件內觸發外部環境的副作用;
3、插槽允許外部環境將額外的內容組合在元件中。
以上這篇Vue 元件複用多次自定義引數操作就是小編分享給大家的全部內容了,希望能給大家一個參考,也希望大家多多支援我們。