<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          【Vue.js 入門到實戰(zhàn)教程】09-Vue 組件插槽 | 父子組件間的內容分發(fā)和插槽作用域

          共 3473字,需瀏覽 7分鐘

           ·

          2020-11-25 02:52

          來源 |?https://xueyuanjun.com/post/21939

          插槽的作用

          在組件入門這篇教程中,學院君已經給大家演示了插槽(slot)功能的基本使用,插槽的主要作用就是在組件中分發(fā)父作用域的內容,這個父作用域可以是 Vue 全局容器(可以看作是一個全局的「根組件」),也可以是父組件。
          說到這里,我們可以引用一張 Vue 官網提供的組件架構圖,實際上,一個 Vue.js 應用就是基于下面這樣的一個組件樹來組織和管理頁面元素的:
          我們可以把全局 Vue 實例看作一個最頂層的隱式組件,其他組件都是通過?Vue.component?在此基礎上注冊,并且這些組件之間可以相互嵌套、內容分發(fā)、數據傳遞以及事件通知來建立聯(lián)系,從而通過一個個小組件自下而上層層疊加,最終構建出復雜的頁面布局和功能模塊。
          關于組件嵌套、數據傳遞和事件通知學院君前面都已經介紹過了,回到插槽這個主題,我們可以通過??語法在子組件中渲染父級作用域定義的元素,從而實現嵌套組件之間的內容分發(fā)。

          命名插槽

          單個插槽在組件入門中已經演示過,如果組件中定義了多個插槽,則可以通過命名插槽的方式來實現內容分發(fā),為了演示這個功能,我們在?vue_learning/component?目錄下新建一個?slot.html?文檔,并編寫示例代碼如下:
          <html><head> <meta charset="UTF-8"> <title>插槽及其作用域使用示例title> <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.5.2/css/bootstrap.min.css" integrity="sha384-JcKb8q3iqJ61gNV9KGb8thSsNjpSL0n8PARn9HuZOnIxN0hoP+VmmDGMN5t9UJ0Z" crossorigin="anonymous"> <script src="https://code.jquery.com/jquery-3.5.1.slim.min.js" integrity="sha384-DfXdz2htPH0lsSSs5nCTpuj/zy4C+OGpamoFVy38MVBnE+IbbVYUew+OrCXaRkfj" crossorigin="anonymous">script> <script src="https://stackpath.bootstrapcdn.com/bootstrap/4.5.2/js/bootstrap.min.js" integrity="sha384-B4gt1jrGC7Jh4AgTPSdUtOBvfO8shuf57BaghqFfPlYxofvL8/KUEfYiJOMMV+rV" crossorigin="anonymous">script> <script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/vue.js">script>head><body><div id="app"> <button type="button" class="btn btn-primary" data-toggle="modal" data-target="#exampleModal"> 模態(tài)框 button>
          <modal-example> <template slot="header">標題template> 主體內容... modal-example>div>
          <script> Vue.component('modal-example', { template: '<div class="modal fade" id="exampleModal" tabindex="-1" aria-labelledby="exampleModalLabel" aria-hidden="true">' + ' <div class="modal-dialog">' + ' <div class="modal-content">' + ' <div class="modal-header">' + ' <h5 class="modal-title" id="exampleModalLabel"><slot name="header">slot>h5>' + ' <button type="button" class="close" data-dismiss="modal" aria-label="Close">' + ' <span aria-hidden="true">×span>' + ' button>' + ' div>' + ' <div class="modal-body">' + ' <slot>slot>' + ' div>' + ' <div class="modal-footer">' + ' <button type="button" class="btn btn-secondary" data-dismiss="modal">Closebutton>' + ' <button type="button" class="btn btn-primary">Save changesbutton>' + ' div>' + ' div>' + ' div>' + 'div>' }); new Vue({ el: '#app' })script>body>html>
          在這段代碼中,我們引入了?Bootstrap?框架來渲染一個模態(tài)框,具體的模態(tài)框部分代碼通過?modal-example?組件來定義,在這個組件中,我們定義了兩個插槽來分發(fā)父級作用域分發(fā)的內容,一個用于渲染模態(tài)框標題,一個用于渲染模態(tài)框主體內容:
          <div class="modal-header"> <h5 class="modal-title" id="exampleModalLabel"> <slot name="header">slot> h5> <button type="button" class="close" data-dismiss="modal" aria-label="Close"> <span aria-hidden="true">×span> button>div><div class="modal-body"> <slot>slot>div>
          對應的父級作用域中,我們通過如下代碼引入?modal-example?組件進行渲染:
          <modal-example> <template slot="header">標題template> 主體內容...modal-example>
          可以看到,對于組件中的命名插槽,需要通過??與之呼應,其中?name?值就是命名插槽對應的?name?屬性值:
          <slot name="header">slot>
          這樣??標簽中對應的內容就會分發(fā)到對應命名插槽中,而??標簽中定義其他的內容則會自動分發(fā)到未命名的插槽中:
          我們在瀏覽器中預覽這個 HTML 文檔,就可以看到對應的渲染效果了:
          當然,你也可以定義多個命名插槽:
          # 視圖部分<modal-example> <template slot="header">標題template> <template slot="body">主體內容...template>modal-example>
          ...
          # 組件模板<div class="modal-header"> <h5 class="modal-title" id="exampleModalLabel"> <slot name="header">slot> h5> ...div><div class="modal-body"> <slot name="body">slot>div>
          效果也是完全一樣的。

          默認內容

          Vue 還支持為插槽定義默認渲染內容,這樣,即便父級作用域沒有定義要分發(fā)的內容,也可以通過默認的內容進行渲染(如果父級作用域定義了要分發(fā)的內容,則會覆蓋插槽中的默認內容):
          # 視圖部分<modal-example>
          modal-example>
          ...
          # 組件模板<div class="modal-header"> <h5 class="modal-title" id="exampleModalLabel"> <slot name="header">默認標題slot> h5> ...div><div class="modal-body"> <slot name="body">默認內容slot>div>
          對應的渲染效果如下:

          作用域

          以上內容分發(fā)都是靜態(tài)的內容渲染,除此之外,我們還可以在父級作用域獲取組件插槽中的動態(tài)數據,從而通過條件過濾實現內容的動態(tài)渲染,你可以將其理解為在父級作用域引用帶有動態(tài)數據的插槽,那如何在父級作用域中調用組件插槽中的數據呢?Vue.js 框架通過作用域插槽的機制對此提供了支持。
          # HTML 視圖
          ...
          # 組件模板Vue.component('modal-example', { props: ['languages'], template: ... + '' + '' + ...});
          重點關注主體內容對應的插槽,我們在父級作用域引用?modal-example?組件時,通過 props 屬性?languages?傳入了要渲染的數據,然后在組件模板對應的插槽中,通過如下代碼渲染傳入的數據:
          我們通過一個循環(huán)列表渲染從父級作用域傳入的?languages?數據,將每一個列表項通過插槽轉發(fā)給父級作用域定義渲染的內容(這里指定了默認的內容,即?{{ language }},如果父級作用域中沒有定義分發(fā)的內容,則使用默認內容渲染)。
          另外,我們還在?slot?標簽上綁定了一個動態(tài)屬性?:language,這一步不可或缺,有了這個綁定才可以在父級作用域引用插槽中的變量數據。
          我們來看父級作用域中分發(fā)內容到該插槽的示例代碼:
          這里,需要通過一個未命名的?template?元素來包裹待分發(fā)內容,然后在這個元素上設置?scope?屬性,聲明對應的插槽作用域為?slotProps,即主體內容部分對應的插槽(只能訪問該插槽綁定的數據)。
          這樣一來,就可以通過?slotProps.language?訪問綁定到該插槽上的?language?變量數據了(當然,你還可以在插槽上綁定更多屬性,然后通過?slotProps?在父級作用域引用它們)。
          在瀏覽器中預覽這個模態(tài)框,渲染效果如下:
          以上就是 Vue.js 組件插槽的基本功能和使用演示。
          到目前為止,我們所有的 Vue 組件都是在單個 HTML 文檔中定義的,如果組件很多、模板代碼很復雜,將會導致代碼可讀性和可維護性很差,這里一個小小的模態(tài)框演示代碼足以窺見端倪。
          為此,Vue.js 生態(tài)提供了 Vue Loader 來支持編寫單文件 Vue 組件,從而方便我們以更加靈活、更加現代的方式構建功能強大的 Vue 應用,下篇教程,學院君將給大家演示如何 Vue CLI + Vue Loader 來編寫單文件 Vue 組件,并成功在 HTML 文檔中引入和渲染。
          本文完~
          推薦閱讀
          【Vue.js 入門到實戰(zhàn)教程】08-Vue 組件通信 | 父子組件之間的數據傳遞和事件監(jiān)聽
          【Vue.js 入門到實戰(zhàn)教程】07-Vue 組件注冊 | 基本使用和組件嵌套
          【Vue.js 入門到實戰(zhàn)教程】06-在 Vue.js 中通過計算屬性動態(tài)設置屬性值

          瀏覽 67
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          評論
          圖片
          表情
          推薦
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  午夜男女操逼视频 | 免费操逼网站 | 欧美性爱69网 | 怡红院在线播放 | 人妻女大香蕉大香蕉 |