做者:Matt Maribojoc
譯者:前端小智
來源:medium
有夢想,有乾貨,微信搜索 【大遷世界】 關注這個在凌晨還在刷碗的刷碗智。html
本文 GitHub https://github.com/qq449245884/xiaozhi 已收錄,有一線大廠面試完整考點、資料以及個人系列文章。前端
VueUse 是 Anthony Fu 大佬的一個開源項目,它爲Vue的開發者提供了大量用於 Vue2 和Vue3 的基本 Composition API 實用工具函數。vue
它有幾十個用於常見開發人員用例的解決方案,如跟蹤ref
更改,檢測元素可見性,簡化常見Vue模式,鍵盤/鼠標輸入等。 這是真正節省開發時間的好方法,由於咱們沒必要本身親手添加全部這些標準功能,拿來主義,用就對了(再次感謝大佬的付出)。react
我喜歡VueUse庫,由於它在決定提供哪些實用工具時真正把開發者放在第一位,並且它是一個維護良好的庫,由於它與Vue的當前版本保持同步。ios
若是你想看到每個實用程序的完整列表,建議去看看官方文檔。但總結一下,VueUse 中有9種類型的函數。git
getters
、conditionals
、ref synchronization
等。VueUse 的最大特色之一是,它只用一個包就能兼容 Vue2 和 Vue3! github
安裝VueUse有兩種選擇:npm
或 CDN
面試
npm i @vueuse/core # yarn add @vueuse/core
<script src="https://unpkg.com/@vueuse/shared"></script> <script src="https://unpkg.com/@vueuse/core"></script>
推薦使用NPM,由於它更容易理解,但若是咱們使用CDN, 可能經過 window.VueUse
來訪問。npm
使用 npm,能夠經過解構的方式來得到想要的方法:segmentfault
import { useRefHistory } from '@vueuse/core'
useRefHistory
跟蹤對 ref
所作的每個改變,並將其存儲在一個數組中。這樣咱們可以輕鬆爲應用程序提供撤銷和重作功能。
來看一個示例,在該示例中,咱們作一個可以撤銷的文本區域
第一步是在沒有 VueUse 的狀況下建立咱們的基本組件--使用ref
、textarea
、以及用於撤銷和重作的按鈕。
<template> <p> <button> Undo </button> <button> Redo </button> </p> <textarea v-model="text"/> </template> <script setup> import { ref } from 'vue' const text = ref('') </script> <style scoped> button { border: none; outline: none; margin-right: 10px; background-color: #2ecc71; color: white; padding: 5px 10px;; } </style>
接着,導入useRefHistory
,而後經過 useRefHistory
從 text
中提取history
、undo
和redo
屬性。
import { ref } from 'vue' import { useRefHistory } from '@vueuse/core' const text = ref('') const { history, undo, redo } = useRefHistory(text)
每當咱們的ref
發生變化,更新history
屬性時,就會觸發一個監聽器。
爲了看看底層作了什麼,咱們把 history
內容打印出來。並在單擊相應按鈕時調用 undo
和redo
函數。
<template> <p> <button @click="undo"> Undo </button> <button @click="redo"> Redo </button> </p> <textarea v-model="text"/> <ul> <li v-for="entry in history" :key="entry.timestamp"> {{ entry }} </li> </ul> </template> <script setup> import { ref } from 'vue' import { useRefHistory } from '@vueuse/core' const text = ref('') const { history, undo, redo } = useRefHistory(text) </script> <style scoped> button { border: none; outline: none; margin-right: 10px; background-color: #2ecc71; color: white; padding: 5px 10px;; } </style>
直接,跑起來,效果以下:
還有不一樣的選項,爲這個功能增長更多的功能。例如,咱們能夠深刻追蹤 reactive 對象,並像這樣限制 history
記錄的數量。
const { history, undo, redo } = useRefHistory(text, { deep: true, capacity: 10, })
onClickOutside
檢測在一個元素以外的任何點擊。根據個人經驗,這個功能最多見的使用狀況是關閉任何模態或彈出窗口。
一般,咱們但願咱們的模態屏蔽網頁的其他部分,以吸引用戶的注意和限制錯誤。然而,若是他們確實點擊了模態以外,咱們但願它關閉。
要作到這一點,只有兩個步驟。
ref
運行onClickOutside
這是一個簡單的組件,使用onClickOutside
彈出窗口。
<template> <button @click="open = true"> Open Popup </button> <div class="popup" v-if='open'> <div class="popup-content" ref="popup"> Lorem ipsum dolor sit amet consectetur adipisicing elit. Corporis aliquid autem reiciendis eius accusamus sequi, ipsam corrupti vel laboriosam necessitatibus sit natus vero sint ullam! Omnis commodi eos accusantium illum? </div> </div> </template> <script setup> import { ref } from 'vue' import { onClickOutside } from '@vueuse/core' const open = ref(false) // state of our popup const popup = ref() // template ref // whenever our popup exists, and we click anything BUT it onClickOutside(popup, () => { open.value = false }) </script> <style scoped> button { border: none; outline: none; margin-right: 10px; background-color: #2ecc71; color: white; padding: 5px 10px;; } .popup { position: fixed; top: ; left: ; width: 100vw; height: 100vh; display: flex; align-items: center; justify-content: center; background: rgba(, , , 0.1); } .popup-content { min-width: 300px; padding: 20px; width: 30%; background: #fff; } </style
結果是這樣的,咱們能夠用咱們的按鈕打開彈出窗口,而後在彈出內容窗口外單擊關閉它。
Vue開發者的一個常見用例是爲一個組件建立一個自定義的v-model
綁定。這也要求咱們的組件接受一個 value
做爲 prop,每當這個 value
被修改,咱們的組件就會向父類發出一個 update
事件。
useVModel
函數將其簡化爲只使用標準的ref
語法。假設咱們有一個自定義的文本輸入,試圖爲其文本輸入的值建立一個v-model
。一般狀況下,咱們必須接受一個 value
的 prop,而後發出一個 change
事件來更新父組件中的數據值。
咱們可使用useVModel
,把它看成一個普通的ref
,而不是使用ref
並調用props.value
和update:value
。這有助於減小咱們須要記住的不一樣語法的數量!
<template> <div> <input type="text" :value="data" @input="update" /> </div> </template> <script> import { useVModel } from '@vueuse/core' export default { props: ['data'], setup(props, { emit }) { const data = useVModel(props, 'data', emit) console.log(data.value) // equal to props.data data.value = 'name' // equal to emit('update:data', 'name') const update = (event) => { data.value = event.target.value } return { data, update } }, } </script>
每當須要訪問value
時,咱們只需調用.value
,useVModel
將從咱們的組件 props 中給咱們提供值。而每當改變對象的值時,useVModel
會向父組件發出一個更新事件。
下面是父組件的一個簡單示例
<template> <div> <p> {{ data }} </p> <custom-input :data="data" @update:data="data = $event" /> </div> </template> <script> import CustomInput from './components/CustomInput.vue' import { ref } from 'vue' export default { components: { CustomInput, }, setup () { const data = ref('hello') return { data } } }
運行結果以下,父方的值老是與子方的輸入保持同步:
當肯定兩個元素是否重疊時,useIntersectionObserver
是很是強大的。這方面的一個很好的用例是檢查一個元素在視口中是否當前可見。
基本上,它檢查目標元素與根元素/文檔相交的百分比。若是這個百分比超過了某個閾值,它就會調用一個回調,肯定目標元素是否可見。
useIntersectionObserver
提供了一個簡單的語法來使用IntersectionObserver API
。咱們所須要作的就是爲咱們想要檢查的元素提供一個模板ref
。
默認狀況下,IntersectionObserver
將以文檔的視口爲根基,閾值爲0.1
--因此當這個閾值在任何一個方向被越過期,咱們的交集觀察器將被觸發。
示例:咱們有一個假的段落,只是在咱們的視口中佔據了空間,目標元素,而後是一個打印語句,打印咱們元素的可見性。
<template> <p> Is target visible? {{ targetIsVisible }} </p> <div class="container"> <div class="target" ref="target"> <h1>Hello world</h1> </div> </div> </template> <script> import { ref } from 'vue' import { useIntersectionObserver } from '@vueuse/core' export default { setup() { const target = ref(null) const targetIsVisible = ref(false) const { stop } = useIntersectionObserver( target, ([{ isIntersecting }], observerElement) => { targetIsVisible.value = isIntersecting }, ) return { target, targetIsVisible, } }, } </script> <style scoped> .container { width: 80%; margin: auto; background-color: #fafafa; max-height: 300px; overflow: scroll; } .target { margin-top: 500px; background-color: #1abc9c; color: white; padding: 20px; } </style>
運行後,對應的值會更新:
咱們還能夠爲咱們的 Intersection Observer 指定更多的選項,好比改變它的根元素、邊距(計算交叉點時對根的邊界框的偏移)和閾值水平。
const { stop } = useIntersectionObserver( target, ([{ isIntersecting }], observerElement) => { targetIsVisible.value = isIntersecting }, { // root, rootMargin, threshold, window // full options in the source: https://github.com/vueuse/vueuse/blob/main/packages/core/useIntersectionObserver/index.ts threshold: 0.5, } )
一樣重要的是,這個方法返回一個 stop
函數,咱們能夠調用這個函數來中止觀察交叉點。若是咱們只想追蹤一個元素在屏幕上第一次可見的時候,這就特別有用。
在這段代碼中,一旦targetIsVisible
被設置爲true
,observer 就會中止,即便咱們滾動離開目標元素,咱們的值也會保持爲 true
。
const { stop } = useIntersectionObserver( target, ([{ isIntersecting }], observerElement) => { targetIsVisible.value = isIntersecting if (isIntersecting) { stop() } }, )
useTransition
是整個VueUse庫中我最喜歡的函數之一。它容許咱們只用一行就能順利地在數值之間進行過渡。
若是使用 useTransition
作一個下面這樣的效果,要怎麼作呢?
咱們能夠經過三個步驟來作到這一點。
ref
變量 count
,初始值爲 0
useTransition
建立一個變量 output
import { ref } from 'vue' import { useTransition, TransitionPresets } from '@vueuse/core' const count = ref(0) const output = useTransition(count , { duration: 3000, transition: TransitionPresets.easeOutExpo, }) count.value = 5000 </script>
而後在 template 中顯示 output
的值:
<template> <h2> <p> Join over </p> <p> {{ Math.round(output) }}+ </p> <p>Developers </p> </h2> </template> <script setup> import { ref } from 'vue' import { useTransition, TransitionPresets } from '@vueuse/core' const count = ref(0) const output = useTransition(count, { duration: 3000, transition: TransitionPresets.easeOutExpo, }) count.value = 5000 </script>
運行結果:
咱們還可使用useTransition
轉換整個數字數組。 使用位置或顏色時,這很是有用。 使用顏色的一個很好的技巧是使用計算的屬性將RGB
值格式化爲正確的顏色語法。
<template> <h2 :style="{ color: color } "> COLOR CHANGING </h2> </template> <script setup> import { ref, computed } from 'vue' import { useTransition, TransitionPresets } from '@vueuse/core' const source = ref([, , ]) const output = useTransition(source, { duration: 3000, transition: TransitionPresets.easeOutExpo, }) const color = computed(() => { const [r, g, b] = output.value return `rgb(${r}, ${g}, ${b})` }) source.value = [255, , 255] </script>
這不是VueUse的完整指南。這些只是我日常比較經常使用的函數,還有不少好用的函數,你們能夠自行到官網去學習使用。
~完,我去刷碗了,週末不刷碗,晚上跪榴蓮。
代碼部署後可能存在的BUG無法實時知道,過後爲了解決這些BUG,花了大量的時間進行log 調試,這邊順便給你們推薦一個好用的BUG監控工具 Fundebug。
原文:https://learvue.co/2021/07/5-...
有夢想,有乾貨,微信搜索 【大遷世界】 關注這個在凌晨還在刷碗的刷碗智。
本文 GitHub https://github.com/qq44924588... 已收錄,有一線大廠面試完整考點、資料以及個人系列文章。