這篇文章帶大家深入了解一下Vue3 Suspense,聊聊Suspense是什麼、能做什麼,以及如何使用它,希望對大家有幫助!
Suspense 不是你想的那樣。是的,它幫助我們處理非同步元件,但它的作用遠不止於此。 (學習影片分享:vue影片教學)
Suspense 允許我們協調整個應用程式的載入狀態,包括所有深度嵌套的元件。而不是像一個爆米花用戶界面一樣,到處都是loading,組件突然奔的一下到位
#有了Suspense, 我們可以有一個單一的、有組織的系統,一次性加載所有東西。
而且,Suspense 也為我們提供了細粒度的控制,所以如果需要的話,我們可以在兩者之間實現一些東西。
在這篇文章中,我們將學到很多關於 Suspense 的知識--它是什麼,能幹什麼,以及如何使用它。
首先,我們將仔細看看這些爆米花介面。然後,在看看如何使用Suspense來解決這些問題。之後,嘗試透過在整個應用程式中嵌套Suspense來獲得更精細的控制。最後,簡單看看如何使用佔位符來豐富我們的使用者介面。
爆米花UI-- Suspense 之前
範例地址:https://codesandbox.io/s/uncoordinated-loading-before-suspense-srh8ll?file= /src/App.vue
如果沒有Suspense,每個元件都必須單獨處理其載入狀態。
這可能會導致一些相當糟糕的使用者體驗,多個載入按鈕和內容突然出現在螢幕上,就像你在製作爆米花一樣。
雖然,我們可以建立抽像元件來處理這些載入狀態,但這比使用Suspense要困難得多。有一個單一的點來管理載入狀態,比每個元件做自己的事情要容易維護得多。
在例子中,我們使用BeforeSuspense
元件來模擬一個內部處理載入狀態的元件。把它命名為BeforeSuspense
,因為一旦我們實作了Suspense,我們就會把它重構為WithSuspense
元件。
BeforeSuspense.vue
<template> <div> <spinner></spinner> <slot></slot> </div> </template> <script> import { ref } from 'vue' import Spinner from './Spinner.vue' const loading = ref(true) const { time } = defineProps({ time: { type: Number, default: 2000 } }) setTimeout(() => (loading.value = false), time) </script>
一開始設定 loading 為 true
,所以顯示 Spinner
元件。然後,當setTimeout
完成後,將 loading 設為 false
,隱藏 Spinner
並使元件的背景為綠色。
在這個元件中,也包含一個slot
,這樣其它元件就可以套在BeforeSuspense
元件中了:
<template> <button>Reload page</button> <beforesuspense> <beforesuspense></beforesuspense> <beforesuspense> <beforesuspense></beforesuspense> <beforesuspense></beforesuspense> </beforesuspense> </beforesuspense> </template>
沒有什麼太花俏的東西。只是一些嵌套的組件,有不同的時間值傳遞給它們。
下面,我們來看看怎麼透過使用 Suspense
元件來改進這個爆米花使用者介面。
Suspense
範例網址:https://codesandbox.io/s/coordinated-loading-with-suspense-b6dcbi?file=/src/App.vue
現在,我們使用Suspense
來處理這些亂七八糟的東西,並將其變成一個更好的使用者體驗。
不過,首先我們需要快速了解Suspense到底是什麼
Suspense 基礎
以下是Suspense 部分的基本架構
<suspense> <!-- Async component here --> <template> <!-- Sync loading state component here --> </template> </suspense>
為了使用Suspense,把非同步元件放入default
槽,把回退載入狀態放入fallback
槽。
非同步元件是以下兩種情況之一:
- 一個帶有
async setup
函數的元件,該元件傳回一個Promise,或在script setup
中使用頂級await
- 使用
defineAsyncComponent
非同步載入的元件
fallback# 槽中的內容。然後,當Promise 被解決時,它會在
default 槽中顯示該非同步元件。
注意: 这里没有错误处理路基。起初我以为有,但这是对悬念的一个常见误解。如果想知道是什么导致了错误。可以使用onErrorCaptured
钩子来捕捉错误,但这是一个独立于Suspense的功能。
现在我们对Suspense有了一些了解,让我们回到我们的演示应用程序。
管理异步依赖关系
为了让Suspense
管理我们的加载状态,首先需要将BeforeSuspense
组件转换成一个异步组件
我们将它命名为 WithSuspense,内容如下:
<template> <div> <!-- 这里不需要一个 Spiner 了,因为加载是在根部处理的 --> <slot></slot> </div> </template> <script> const { time } = defineProps({ time: { type: Number, required: true } }) // 加入一个延迟,以模拟加载数据 await new Promise(resolve => { setTimeout(() => { resolve() }, time) }) </script>
我们已经完全删除了加载状态的Spinner,因为这个组件不再有加载状态了。
因为这是一个异步组件,setup
函数直到它完成加载才会返回。该组件只有在 setup 函数完成后才会被加载。因此,与BeforeSuspense
组件不同,WithSuspense
组件内容在加载完毕之前不会被渲染。
这对任何异步组件来说都是如此,不管它是如何被使用的。在setup函数返回(如果是同步的)或解析(如果是异步的)之前,它不会渲染任何东西。
有了WithSuspense组件,我们仍然需要重构我们的App
组件,以便在Suspens
e组件中使用这个组件。
<template> <button>Reload page</button> <suspense> <withsuspense> <withsuspense></withsuspense> <withsuspense> <withsuspense></withsuspense> <withsuspense></withsuspense> </withsuspense> </withsuspense> <template> <spinner></spinner> </template> </suspense> </template>
结构和之前一样,但这次是在 Suspense 组件的默认槽中。我们还加入了 fallback 槽,在加载时渲染我们的Spinner组件。
在演示中,你会看到它显示加载按钮,直到所有的组件都加载完毕。只有在那时,它才会显示现在完全加载的组件树。
异步瀑布
如果你仔细注意,你会注意到这些组件并不像你想象的那样是并联加载的。
总的加载时间不是基于最慢的组件(5秒)。相反,这个时间要长得多。这是因为Vue只有在父异步组件完全解析后才会开始加载子组件。
你可以通过把日志放到WithSuspense组
件中来测试这一点。一个在安装开始跟踪安装,一个在我们调用解决之前。
最初使用BeforeSuspense
组件的例子中,整个组件树被挂载,无需等待,所有的 "异步 "操作都是并行启动的。这意味着Suspense
有可能通过引入这种异步瀑布而影响性能。所以请记住这一点。
嵌套 Suspense 以隔离子树
事例地址:https://codesandbox.io/s/nesting-suspense-wt0q7k?file=/src/App.vue
这里有一个深度嵌套的组件,它需要整整5秒来加载,阻塞了整个UI,尽管大多数组件加载完成的时间要早得多。
但对我们来说有一个解决方案
通过进一步嵌套第二个Suspense组件,我们可以在等待这个组件完成加载时显示应用程序的其他部分。
<template> <button>Reload page</button> <suspense> <withsuspense> <withsuspense></withsuspense> <withsuspense> <withsuspense></withsuspense> <!-- Nest a second Suspense component --> <suspense> <withsuspense></withsuspense> <template> <spinner></spinner> </template> </suspense> </withsuspense> </withsuspense> <template> <spinner></spinner> </template> </suspense> </template>
将其包裹在第二个Suspense
组件中,使其与应用程序的其他部分隔离。Suspense组件本身是一个同步组件,所以当它的父级组件被加载时,它就会被加载。
然后它将显示它自己的 fallback 内容,直到5秒结束。
通过这样做,我们可以隔离应用程序中加载较慢的部分,减少我们的首次交互时间。在某些情况下,这可能是必要的,特别是当你需要避免异步瀑布时。
从功能的角度来看,这也是有意义的。你的应用程序的每个功能或 "部分"都可以被包裹在它自己的Suspense
组件中,所以每个功能的加载都是一个单一的逻辑单元。
当然,如果你用 "Suspense" 包装每一个组成部分,我们就会回到我们开始的地方。我们可以选择以任何最合理的方式来批处理我们的加载状态。
使用占位符的 Suspense
事例地址: https://codesandbox.io/s/placeholders-and-suspense-k5uzw0?
与其使用单一的 spinner,占位符组件往往可以提供更好的体验。
这种方式向用户展示将要展示的内容,并让他们在界面渲染前有一种期待的感觉。这是 spinner 无法做到的。
可以说--它们很时髦,看起来很酷。因此,我们重构代码,使用占位符方式:
<template> <button>Reload page</button> <suspense> <withsuspense> <withsuspense></withsuspense> <withsuspense> <withsuspense></withsuspense> <suspense> <withsuspense></withsuspense> <template> <placeholder></placeholder> </template> </suspense> </withsuspense> </withsuspense> <template> <!-- 这里,复制实际数据的形状 --> <placeholder> <placeholder></placeholder> <placeholder> <placeholder></placeholder> <placeholder></placeholder> </placeholder> </placeholder> </template> </suspense> </template>
我们安排了这些Placeholder组件,并对它们进行了风格化处理,使它们看起来与WithSuspense
组件完全一样。这提供了一个在加载和装载状态之间的无缝过渡。
在演示中,Placeholder
组件在背景上给我们提供了一个CSS动画,以创造一个脉动的效果:
.fast-gradient { background: linear-gradient( to right, rgba(255, 255, 255, 0.1), rgba(255, 255, 255, 0.4) ); background-size: 200% 200%; animation: gradient 2s ease-in-out infinite; } @keyframes gradient { 0% { background-position: 0% 50%; } 50% { background-position: 100% 50%; } 100% { background-position: 0% 50%; } }
总结
爆米花的加载状态是非常明显的,会伤害用户体验。
幸运的是,Suspense 是一个很棒的新特性,它为我们在Vue应用程序中协调加载状态提供了很多选择。
然而,在写这篇文章的时候,Suspense仍然被认为是实验性的,所以要谨慎行事。关于它的状态的最新信息,请参考文档。
以上是詳解Vue3 Suspense:是什麼?能幹什麼?如何用?的詳細內容。更多資訊請關注PHP中文網其他相關文章!

Vue.js是由尤雨溪在2014年發布的漸進式JavaScript框架,用於構建用戶界面。它的核心優勢包括:1.響應式數據綁定,數據變化自動更新視圖;2.組件化開發,UI可拆分為獨立、可複用的組件。

Netflix使用React作為其前端框架。 1)React的組件化開發模式和強大生態系統是Netflix選擇它的主要原因。 2)通過組件化,Netflix將復雜界面拆分成可管理的小塊,如視頻播放器、推薦列表和用戶評論。 3)React的虛擬DOM和組件生命週期優化了渲染效率和用戶交互管理。

Netflix在前端技術上的選擇主要集中在性能優化、可擴展性和用戶體驗三個方面。 1.性能優化:Netflix選擇React作為主要框架,並開發了SpeedCurve和Boomerang等工具來監控和優化用戶體驗。 2.可擴展性:他們採用微前端架構,將應用拆分為獨立模塊,提高開發效率和系統擴展性。 3.用戶體驗:Netflix使用Material-UI組件庫,通過A/B測試和用戶反饋不斷優化界面,確保一致性和美觀性。

NetflixusesAcustomFrameworkcalled“ Gibbon” BuiltonReact,notReactorVuedIrectly.1)TeamSperience:selectBasedonFamiliarity.2)ProjectComplexity:vueforsimplerprojects:reactforforforproproject,reactforforforcompleplexones.3)cocatizationneedneeds:reactoffipicatizationneedneedneedneedneedneeds:reactoffersizationneedneedneedneedneeds:reactoffersizatization needefersmoreflexibleise.4)

Netflix在框架選擇上主要考慮性能、可擴展性、開發效率、生態系統、技術債務和維護成本。 1.性能與可擴展性:選擇Java和SpringBoot以高效處理海量數據和高並發請求。 2.開發效率與生態系統:使用React提升前端開發效率,利用其豐富的生態系統。 3.技術債務與維護成本:選擇Node.js構建微服務,降低維護成本和技術債務。

Netflix主要使用React作為前端框架,輔以Vue用於特定功能。 1)React的組件化和虛擬DOM提升了Netflix應用的性能和開發效率。 2)Vue在Netflix的內部工具和小型項目中應用,其靈活性和易用性是關鍵。

Vue.js是一種漸進式JavaScript框架,適用於構建複雜的用戶界面。 1)其核心概念包括響應式數據、組件化和虛擬DOM。 2)實際應用中,可以通過構建Todo應用和集成VueRouter來展示其功能。 3)調試時,建議使用VueDevtools和console.log。 4)性能優化可通過v-if/v-show、列表渲染優化和異步加載組件等實現。

Vue.js適合小型到中型項目,而React更適用於大型、複雜應用。 1.Vue.js的響應式系統通過依賴追踪自動更新DOM,易於管理數據變化。 2.React採用單向數據流,數據從父組件流向子組件,提供明確的數據流向和易於調試的結構。


熱AI工具

Undresser.AI Undress
人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool
免費脫衣圖片

Clothoff.io
AI脫衣器

AI Hentai Generator
免費產生 AI 無盡。

熱門文章

熱工具

Atom編輯器mac版下載
最受歡迎的的開源編輯器

PhpStorm Mac 版本
最新(2018.2.1 )專業的PHP整合開發工具

禪工作室 13.0.1
強大的PHP整合開發環境

WebStorm Mac版
好用的JavaScript開發工具

SublimeText3 Mac版
神級程式碼編輯軟體(SublimeText3)