<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>

          使用CSS自定義屬性實(shí)現(xiàn)骨架屏

          共 11022字,需瀏覽 23分鐘

           ·

          2022-06-25 15:59


          點(diǎn)擊上方 前端陽(yáng)光,關(guān)注公眾號(hào)

          回復(fù)加群,加入技術(shù)交流群交流群


          • 原文地址:https://css-tricks.com/building-skeleton-screens-css-custom-properties/
          • 原文作者:Tapas Adhikary
          • 譯者:陽(yáng)光是sunny

          1前言

          其實(shí)這篇文章網(wǎng)上已經(jīng)有翻譯版本,但是讀起來(lái)明顯是機(jī)翻的,實(shí)在是受不了,于是就用自己的理解翻譯了一下

          2正文

          項(xiàng)目要不要加載loading狀態(tài)通常是在項(xiàng)目完成后才考慮的事情,當(dāng)然,有時(shí)候直接就不考慮了。

          開(kāi)發(fā)人員的職責(zé)不只是提高性能,同時(shí)優(yōu)化網(wǎng)絡(luò)差時(shí),請(qǐng)求接口緩慢導(dǎo)致的頁(yè)面的慢渲染也是非常重要的。

          3速度的錯(cuò)覺(jué)

          隨著我們對(duì)移動(dòng)體驗(yàn)的期望的變化,我們對(duì)性能的理解也在變化。我們期望,無(wú)論當(dāng)前的網(wǎng)絡(luò)如何,web頁(yè)面都能像原生應(yīng)用程序一樣順滑,一樣快速響應(yīng)。

          骨架屏的出現(xiàn)。這個(gè)想法使得用戶更有耐心,因?yàn)樗麄冎勒诎l(fā)生什么,并且在內(nèi)容實(shí)際存在之前能夠預(yù)測(cè)內(nèi)容,那么他們會(huì)認(rèn)為系統(tǒng)更快。這在很大程度上保持了用戶等待的熱情。

          骨架屏??

          這個(gè)概念可能包括顯示文本,圖像或其他內(nèi)容元。可以在網(wǎng)上可以看到骨架屏的使用已經(jīng)非常廣泛,F(xiàn)acebook,Google,Slack等公司都在使用。

          4舉個(gè)例子

          假設(shè)你正在構(gòu)建一個(gè)旅行相關(guān)的Web應(yīng)用程序,用戶可以分享他們的旅行以及推薦的地點(diǎn),它的主要內(nèi)容可能看起來(lái)像這樣:

          您可以將該卡片簡(jiǎn)化到其基本視覺(jué)形狀(UI組件的骨架)

          每當(dāng)有人從服務(wù)器請(qǐng)求新內(nèi)容時(shí),您可以立即開(kāi)始顯示骨架,同時(shí)在后臺(tái)加載數(shù)據(jù)。內(nèi)容準(zhǔn)備就緒后,只需將骨架換成實(shí)際卡即可。

          您可以使用圖像來(lái)顯示骨架,但這會(huì)引入額外的請(qǐng)求和數(shù)據(jù)開(kāi)銷。我們本身已經(jīng)在這里加載了東西,所以還要去等待另一個(gè)圖像先加載,這可不是一個(gè)好主意。另外圖片不是響應(yīng)式的,如果我們決定調(diào)整卡片的樣式,我們將不得不更改骨架圖像,以便它們?cè)俅纹ヅ洹??。

          一個(gè)更好的解決方案是只用 CSS 創(chuàng)建骨架屏。沒(méi)有額外的請(qǐng)求,最小的開(kāi)銷。而且以后修改更加的方便快捷。

          5CSS 中繪制骨架

          首先,我們需要繪制構(gòu)成卡片骨架的基本形狀。

          我們可以通過(guò)向background-image屬性添加不同的漸變來(lái)做到這一點(diǎn)。默認(rèn)情況下,線性漸變從上到下運(yùn)行,具有不同的顏色過(guò)渡。如果我們只定義一個(gè)色標(biāo),其余的保持透明,我們就可以繪制形狀。

          請(qǐng)記住,多個(gè)背景圖像在這里堆疊在一起,因此順序很重要。最后一個(gè)漸變定義將展示在后面,最先定義的展示在前面。

          .skeleton {
            background-repeat: no-repeat;
            background-image
              /* layer 2: avatar */
              /* white circle with 16px radius */
              radial-gradient(circle 16px, white 99%, transparent 0),
              /* layer 1: title */
              /* white rectangle with 40px height */
              linear-gradient(white 40px, transparent 0),
              /* layer 0: card bg */
              /* gray rectangle that covers whole element */
              linear-gradient(gray 100%, transparent 0);
          }

          這些元素通過(guò)拉伸來(lái)填充整個(gè)空間,就像常規(guī)的塊級(jí)元素一樣。如果我們想要改變它,我們必須為它們定義明確的尺寸。background-size的值來(lái)設(shè)置每個(gè)圖層的寬度和高度,background-size的值的順序保持我們使用的background-image順序相同

          .skeleton {
            background-size:
              32px 32px,  /* 頭像 */
              200px 40px,  /* 標(biāo)題 */
              100% 100%/* 卡片背景 */
          }

          最后一步是將元素定位在卡片上。這與position:absolute類似,跟它的left和top屬性的值一樣。例如:我們可以給頭像和標(biāo)題 模擬 padding:24px,以匹配真實(shí)卡片的外觀。

          .skeleton {
            background-position:
              24px 24px,  /* 頭像 */
              24px 200px/* 標(biāo)題 */
              0 0;        /* 卡片背景 */
          }

          6使用自定義屬性

          如果我們想構(gòu)建一些稍微復(fù)雜一點(diǎn)的東西,CSS 很快就會(huì)變得混亂并且很難閱讀。如果將代碼交給其他開(kāi)發(fā)人員,他們將不知道所有這些神奇數(shù)字的來(lái)源。維護(hù)它肯定會(huì)很糟糕。

          值得慶幸的是,我們現(xiàn)在可以使用CSS 自定義屬性,以更簡(jiǎn)潔、對(duì)開(kāi)發(fā)人員更友好的方式來(lái)編寫骨架樣式。

          .skeleton {
            /*
              define as separate properties
            */

            --card-height340px;
            --card-padding:24px;
            --card-skeletonlinear-gradient(gray var(--card-height), transparent 0);

            --title-height32px;
            --title-width200px;
            --title-positionvar(--card-padding) 180px;
            --title-skeletonlinear-gradient(white var(--title-height), transparent 0);

            --avatar-size32px;
            --avatar-positionvar(--card-padding) var(--card-padding);
            --avatar-skeletonradial-gradient(
              circle calc(var(--avatar-size) / 2), 
              white 99%
              transparent 0
            );

            /* 
              now we can break the background up 
              into individual shapes 
            */

            background-image
              var(--avatar-skeleton),
              var(--title-skeleton),
              var(--card-skeleton);

            background-size:
              var(--avatar-size),
              var(--title-width) var(--title-height),
              100% 100%;

            background-position:
              var(--avatar-position),
              var(--title-position),
              0 0;
          }

          這不僅更具可讀性,而且以后更改一些值也更容易。另外,我們可以使用一些變量(像 --avatar-size、--card-padding等)來(lái)定義實(shí)際卡片的樣式,并始終使其與骨架版本保持同步。

          添加一個(gè)媒體查詢來(lái)調(diào)整不同斷點(diǎn)的部分骨架現(xiàn)在也很簡(jiǎn)單:

          @media screen and (min-width: 47em) {
            :root {
              --card-padding32px;
              --card-height360px;
            }
          }

          瀏覽器對(duì)自定義屬性的支持很好,但不是 100%。基本上,所有現(xiàn)代瀏覽器都支持,IE/Edge 有點(diǎn)晚了。對(duì)于這個(gè)特定的用例,很容易使用 Sass 變量添加回退。

          7添加動(dòng)畫

          為了使它更好,我們可以為我們的骨架設(shè)置動(dòng)畫,讓它看起來(lái)更像一個(gè)加載指示器。我們需要做的就是在頂層放置一個(gè)新的漸變,然后用@keyframes.

          這是完成骨架卡外觀的完整示例:

          可以查看預(yù)覽:https://codepen.io/mxbck/pen/EvmLVp

          <div class="card"></div>

          /*
           * Variables
           */


          :root {  
            --card-padding24px;
            --card-height340px;
            --card-skeletonlinear-gradient(lightgrey var(--card-height), transparent 0);
            
            --avatar-size32px;
            --avatar-positionvar(--card-padding) var(--card-padding);
            --avatar-skeletonradial-gradient(circle 16px at center, white 99%, transparent 0
            );
            
            --title-height32px;
            --title-width200px;
            --title-positionvar(--card-padding) 180px;
            --title-skeletonlinear-gradient(white var(--title-height), transparent 0);
            
            --desc-line-height16px;
            --desc-line-skeletonlinear-gradient(white var(--desc-line-height), transparent 0);
            --desc-line-1-width:230px;
            --desc-line-1-positionvar(--card-padding) 242px;
            --desc-line-2-width:180px;
            --desc-line-2-positionvar(--card-padding) 265px;
            
            --footer-height40px;
            --footer-position0 calc(var(--card-height) - var(--footer-height));
            --footer-skeletonlinear-gradient(white var(--footer-height), transparent 0);
            
            --blur-width200px;
            --blur-sizevar(--blur-width) calc(var(--card-height) - var(--footer-height));
          }

          /*
           * Card Skeleton for Loading
           */


          .card {
            width280px; //demo
            heightvar(--card-height);
            
            &:empty::after {
              content:"";
              display:block;
              width100%;
              height100%;
              border-radius:6px;
              box-shadow0 10px 45px rgba(0,0,0, .1);

              background-image:
                linear-gradient(
                  90deg
                  rgba(lightgrey, 00
                  rgba(lightgrey, .850%
                  rgba(lightgrey, 0100%
                ),                          //animation blur
                var(--title-skeleton),      //title
                var(--desc-line-skeleton),  //desc1
                var(--desc-line-skeleton),  //desc2
                var(--avatar-skeleton),     //avatar
                var(--footer-skeleton),     //footer bar
                var(--card-skeleton)        //card
              ;

              background-size:
                var(--blur-size),
                var(--title-width) var(--title-height),
                var(--desc-line-1-width) var(--desc-line-height),
                var(--desc-line-2-width) var(--desc-line-height),
                var(--avatar-size) var(--avatar-size),
                100% var(--footer-height),
                100% 100%
              ;
              
              background-position:
                -150% 0,                      //animation
                var(--title-position),        //title
                var(--desc-line-1-position),  //desc1
                var(--desc-line-2-position),  //desc2
                var(--avatar-position),       //avatar
                var(--footer-position),       //footer bar
                0 0                           //card
              ;

              background-repeat: no-repeat;
              animation: loading 1.5s infinite;
            }
          }

          @keyframes loading {
            to {
              background-position:
                350% 0,        
                var(--title-position),  
                var(--desc-line-1-position),
                var(--desc-line-2-position),
                var(--avatar-position),
                var(--footer-position),
                0 0
              ;
            }
          }


          /* 
           * Demo Stuff
           */


          body {
            min-height:100vh;
            background-color:#FFF;
            display:flex;
            justify-content:center;
            align-items:center;
          }


          往期推薦


          優(yōu)秀文章匯總:https://github.com/Sunny-lucking/blog

          內(nèi)推:https://www.yuque.com/peigehang/kb

          技術(shù)交流群


          我組建了技術(shù)交流群,里面有很多 大佬,歡迎進(jìn)來(lái)交流、學(xué)習(xí)、共建。回復(fù) 加群 即可。后臺(tái)回復(fù)「電子書」即可免費(fèi)獲取 27本 精選的前端電子書!回復(fù)內(nèi)推,可內(nèi)推各廠內(nèi)推碼



             “分享、點(diǎn)贊在看” 支持一波??

          瀏覽 76
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          評(píng)論
          圖片
          表情
          推薦
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          <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>
                  夜色福利在线看 | 久久综合第一页 | 日本黄色软件视频 | 青娱乐成人电影 | 男女h网站 |