国产成人精品18p,天天干成人网,无码专区狠狠躁天天躁,美女脱精光隐私扒开免费观看

Vue3 style CSS 變量注入的實(shí)現

發(fā)布時(shí)間:2021-08-17 12:16 來(lái)源: 閱讀:0 作者:guangzan 欄目: JavaScript 歡迎投稿:712375056

目錄

    摘要

    在單文件組件樣式中支持使用組件狀態(tài)驅動(dòng)的 CSS 變量( CSS 自定義屬性)。

    基礎示例

    <template>
      <div class="text">hello</div>
    </template>
    
    <script>
      export default {
        data() {
          return {
            color: 'red',
            font: {
              size: '2em',
            },
          }
        },
      }
    </script>
    
    <style>
      .text {
        color: v-bind (color);
    
        /* expressions (wrap in quotes) */
        font-size: v-bind ('font.size');
      }
    </style>
    
    

    動(dòng)機

    Vue SFC 樣式提供了直接的 CSS 搭配和封裝,但它是純粹的靜態(tài)的 —— 這意味著(zhù)到目前為止,我們沒(méi)有能力在運行時(shí)根據組件的狀態(tài)動(dòng)態(tài)更新樣式。

    現在,隨著(zhù)大多數現代瀏覽器支持原生 CSS 變量,我們可以利用它來(lái)輕松連接組件的狀態(tài)和樣式。

    設計細節

    SFC 中的標簽現在支持一個(gè)自定義 CSS 函數 v-bind:

    <!-- in Vue SFC -->
    <style>
      .text {
        color: v-bind (color);
      }
    </style>
    

    正如預期的那樣,這將把聲明的值綁定到組件狀態(tài)的屬性上,reactively.color color

    該函數內部可以支持任意的 JavaScript 表達式,但由于 JavaScript 表達式可能包含在 CSS 標識符中無(wú)效的字符,因此在大多數情況下需要用引號來(lái)包裹它們:v-bind

    .text {
      font-size: v-bind ('theme.font.size');
    }
    

    當檢測到這種 CSS 變量時(shí),SFC 編譯器將執行以下操作:

    重寫(xiě)到一個(gè)帶有哈希變量名稱(chēng)的本機。上面的內容將被改寫(xiě)為:v-bind () var ()

    .text {
      color: var (--6b53742-color);
      font-size: var (--6b53742-theme_font_size);
    }
    

    請注意,hash 將應用于所有情況,無(wú)論標簽是否有范圍。這意味著(zhù)注入的 CSS 變量不會(huì )意外地泄漏到子組件中。

    相應的變量將作為內聯(lián)樣式被注入到組件的根元素中。對于上面的例子,最終渲染的 DOM 將看起來(lái)像這樣:

    <div style="--6b53742-color:red;--6b53742-theme_font_size:2em;" class="text">
      hello
    </div>

    注入是響應式的 ——所以如果組件的屬性發(fā)生變化,注入的 CSS 變量將被相應地更新。這種更新是獨立于組件的模板更新的,所以對一個(gè)純 CSS 的響應式屬性的改變不會(huì )觸發(fā)模板的重新渲染。

    編譯細節

    為了注入 CSS 變量,編譯器需要生成并注入如下代碼到組件的 setup ()

    import { useCssVars } from 'vue'
    
    export default {
      setup() {
        //...
        useCssVars(_ctx => ({
          color: _ctx.color,
          theme_font_size: _ctx.theme.font.size,
        }))
      },
    }
    

    ... 這里,運行時(shí)幫助器設置了一個(gè)將變量響應性地應用到 DOM.useCssVars watchEffect 上。

    該編譯策略要求腳本編譯時(shí)首先對標簽內容進(jìn)行簡(jiǎn)單的重碼解析,以確定要暴露的變量列表。然而,這個(gè)解析階段不會(huì )像基于 AST 的完整解析 <style> 那樣耗費開(kāi)銷(xiāo)。

    在生產(chǎn)中,變量名可以被進(jìn)一步 hash,以減少 CSS 的占用。

    .text {
      color: var (--x3b2fs2);
      font-size: var (--29fh29g);
    }
    

    相應的生成的 JavaScript 代碼將相應地使用相同的哈希值。

    采用策略

    這是一個(gè)完全向后兼容的新功能。然而,我們應該明確指出,它依賴(lài)于本地的 CSS 變量,所以用戶(hù)需要了解瀏覽器的支持范圍。

    實(shí)踐

    在 script 中聲明兩個(gè)響應式的屬性,分別是 wallpaperBlur 和 wallpaperMask。wallpaperBlur 表示壁紙的模糊程度, wallpaperMask 表示遮罩的透明度。通過(guò) v-bind 將它們應用到 style,這意味著(zhù)當我們在 script 中改變這兩個(gè)值時(shí),樣式會(huì )響應更改。

    // script
    const wallpaperBlur = ref('0px')
    const wallpaperMask = ref('rgba(0, 0, 0, 0)')
    
    // style
    .wallpaper {
      filter: blur(v-bind(wallpaperBlur));
      bottom: calc(v-bind(wallpaperBlur) * -2);
      left: calc(v-bind(wallpaperBlur) * -2);
      right: calc(v-bind(wallpaperBlur) * -2);
      top: calc(v-bind(wallpaperBlur) * -2);
      .wallpaper-image {
        transition: background-image 0.6s, background-color 0.4s;
      }
      .wallpaper-mask {
        background-color: v-bind(wallpaperMask);
      }
    }
    

    提示

    綁定恰當的屬性

    在上面的例子中,你可能想到到更改遮罩的透明度僅需要聲明一個(gè) 0-1 的數字,之后在 style 中這樣寫(xiě):

    .wallpaper-mask {
      background-color: rgba(0, 0, 0, v-bind(wallpaperMask));
    }
    

    上文已經(jīng)提到在編譯階段會(huì )將 style 中的 v-bind 改寫(xiě)為 CSS 變量的形式,上面的代碼會(huì )被改寫(xiě)為這樣:

    .wallpaper-mask {
      background-color: rgba(0, 0, 0, var (--[hash]-wallpaper_mask));
    }
    

    rgba(0, 0, 0, var (--[hash]-wallpaper_mask)) 在 CSS 中是無(wú)法被解析的。所以這就是為什么將 wallpaperMask 的初始值聲明為 rgba(0, 0, 0, 0) 的原因。這是需要十分注意的一點(diǎn),CSS 中還有許多類(lèi)似的情況。

    注意 style 的更新

    在設計細節中提到相應的變量將作為內聯(lián)樣式被注入到組件的根元素中。最終渲染的 DOM 將看起來(lái)像這樣:

    <div style="--6b53742-color:red;--6b53742-theme_font_size:2em;"></div>
    

    當你在 <script> 中改變 <style> 中綁定的屬性時(shí),內斂樣式中的 CSS 變量將會(huì )響應更改。但是,并不能單獨更新內斂樣式其中的一個(gè) CSS 變量,這意味著(zhù)更新一個(gè)組件中的任意一個(gè)“動(dòng)態(tài)樣式”,都將引起根組件中的內斂樣式全部更新。當 style 屬性的值包含大量 CSS 變量時(shí),你需要考慮重新組織組件。因為編譯生成的 CSS 變量都將作為內聯(lián)樣式被注入到組件的根元素中,我們無(wú)法控制這種行為,將一個(gè)引起更新的 CSS 變量和其他 CSS 變量解耦。

    試想這種情況, style 中編譯生成的 CSS 變量中包含一個(gè)其值為龐大的 base64 的 CSS 變量。當更新該組件中其他 CSS 變量時(shí),整個(gè) style 都將更新,這將帶來(lái)額外的硬件開(kāi)銷(xiāo)。我們需要將這個(gè)生成 base64 CSS 變量的組件單獨抽離,以使該 CSS 變量注入到該組件的根元素,不受其他 CSS 變量更新影響。

    參考資料


    到此這篇關(guān)于Vue3 style CSS 變量注入的實(shí)現的文章就介紹到這了,更多相關(guān)Vue3 style CSS變量注入內容請搜索腳本之家以前的文章或繼續瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

    免責聲明:本站發(fā)布的內容(圖片、視頻和文字)以原創(chuàng )、來(lái)自本網(wǎng)站內容采集于網(wǎng)絡(luò )互聯(lián)網(wǎng)轉載等其它媒體和分享為主,內容觀(guān)點(diǎn)不代表本網(wǎng)站立場(chǎng),如侵犯了原作者的版權,請告知一經(jīng)查實(shí),將立刻刪除涉嫌侵權內容,聯(lián)系我們QQ:712375056,同時(shí)歡迎投稿傳遞力量。

    欧美老妇毛茸茸二毛| 亚洲国产精品成人久久蜜臀| 午夜神器成在线人成在线人| 人妻系列无码专区免费视频| 国产精品成人观看视频国产奇米| 国产精品亚洲专区无码WEB|