Vueuse 是一个功能强大的 Vue.js 生态系统工具库,提供了可重用的组件和函数,帮助开发者更轻松地构建复杂的应用程序。
官网 :https://vueuse.org/core/useWindowScroll/
安装 VueUse
bash
npm i @vueuse/core @vueuse/components
(可选)安装自动导入,添加到 imports 中
json
// 需自动导入方法的库
imports: [
'vue',
'pinia',
'@vueuse/core',
'@vueuse/components'
]
工具库
获取鼠标坐标 useMouse()
html
<script setup lang="ts">
const { x, y } = useMouse()
</script>
<template>
<div>
<p>x:{{ x }}</p>
<p>y:{{ y }}</p>
</div>
</template>
监听鼠标按下 useMousePressed()
html
<script setup>
const { pressed } = useMousePressed()
</script>
<template>
<p>{{ pressed }}</p>
</template>
获取鼠标选择的文字 useTextSelection()
html
<script setup>
const state = useTextSelection()
</script>
<template>
<p>一段供鼠标选择的文字</p>
<p>被鼠标选择的文字是:{{ state.text }}</p>
</template>
窗口滚动条 useWindowScroll()
ts
// 获取滚动条坐标
const { x, y } = useWindowScroll({ behavior: 'smooth' })
html
<!-- 滚动滚动条 -->
<button @click="x += 200">向右滚动 200 px</button>
<button @click="y += 200">向下滚动 200 px</button>
<!-- 滚动滚动条到指定位置 -->
<button @click="y = 600">向下滚动到 600 px</button>
元素滚动条 useScroll()
ts
const el = ref<HTMLElement | null>(null)
const { x, y, isScrolling, arrivedState, directions } = useScroll(el)
html
<div ref="el" />
获取窗口大小 useWindowSize()
ts
const { width, height } = useWindowSize()
添加事件监听 useEventListener
html
<script setup lang="ts">
let num = ref(0)
// 监听鼠标移动
useEventListener('mousemove', () => {
num.value++
})
</script>
<template>
<div class="p-20">
<p>num:{{ num }}</p>
</div>
</template>
- 组件卸载时,监听事件会自动被移除
复制到剪贴板 useClipboard()
html
<script setup lang="ts">
const { copy, copied, isSupported, text } = useClipboard()
let msg = '你好'
async function doCopy() {
copy(msg)
if (copied) {
alert('已复制到剪贴板!')
}
}
</script>
<template>
<div class="p-20">
<p>{{ msg }}</p>
<p v-if="text">已复制到剪贴板的内容:{{ text }}</p>
<button v-if="isSupported" @click="doCopy">复制</button>
</div>
</template>
- copy 复制的方法
- copied 是否完成复制
- isSupported 浏览器是否支持复制到剪贴板
- text 复制到剪贴板的内容
选择本地文件 useFileDialog()
html
<script setup lang="ts">
const { files, open, reset, onChange } = useFileDialog()
onChange((files) => {
console.log(files)
})
</script>
<template>
<button type="button" @click="open()">选择文件</button>
<button type="button" :disabled="!files" @click="reset()">清空选择</button>
<template v-if="files">
<p>
已选择 <b>{{ `${files.length}` }}</b> 个文件
</p>
<li v-for="file of files" :key="file.name">
{{ file.name }}
</li>
</template>
</template>
切换全屏模式 useFullscreen()
html
<script setup lang="ts">
const { isFullscreen, enter, exit, toggle } = useFullscreen()
</script>
<template>
<button v-if="isFullscreen" @click="exit">退出全屏</button>
<button v-else @click="enter">全屏</button>
<button @click="toggle">切换全屏模式</button>
</template>
图片加载 useImage
html
<script setup>
const avatarUrl = 'https://place.dog/300/200'
const { isLoading, error } = useImage({ src: avatarUrl })
</script>
<template>
<span v-if="isLoading">图片加载中...</span>
<span v-else-if="error">图片加载失败</span>
<img v-else :src="avatarUrl" />
</template>
获取联网信息 useNetwork()
ts
const { isOnline, offlineAt, downlink, downlinkMax, effectiveType, saveData, type } = useNetwork()
判断是否联网 useOnline()
ts
const online = useOnline()
给元素添加动画 useOnline()
html
<script setup>
const el = ref()
const {
isSupported,
animate,
// actions
play,
pause,
reverse,
finish,
cancel,
// states
pending,
playState,
replaceState,
startTime,
currentTime,
timeline,
playbackRate
} = useAnimate(el, { transform: 'rotate(360deg)' }, 1000)
</script>
<template>
<div class="p-40">
<span ref="el" style="display: inline-block">旋转360度</span>
</div>
</template>
可控的计时器 useIntervalFn()
html
<script setup>
let num = ref(0)
const { pause, resume, isActive } = useIntervalFn(() => {
num.value++
}, 1000)
</script>
<template>
<div class="p-40">
<div>
{{ num }}
</div>
<button v-if="isActive" @click="pause">暂停计时器</button>
<button v-else @click="resume">恢复计时器</button>
</div>
</template>
暂停代码执行 promiseTimeout
ts
import { promiseTimeout } from '@vueuse/core'
async function print() {
// 开启 console 的默认计时器
console.time()
// 打印当前 console默认计时器 的时间
console.timeLog()
// 等待1s后执行
await promiseTimeout(1000)
// 打印当前 console默认计时器 的时间
console.timeLog()
}
print()
获取网页标题 useTitle()
ts
const title = useTitle()
console.log(title.value) // 打印当前网页的标题
更多工具可参考官网,持续更新中!
组件库
图片加载 UseImage
html
<script setup lang="ts">
import { UseImage } from '@vueuse/components'
</script>
<template>
<UseImage src="https://place.dog/300/200">
<!-- 建议优化为图片加载动画 -->
<template #loading> 图片加载中.. </template>
<template #error> 图片加载失败 </template>
</UseImage>
</template>
一键复制到剪贴板 UseClipboard
html
<script setup lang="ts">
import { UseClipboard } from '@vueuse/components'
</script>
<template>
<UseClipboard v-slot="{ copy, copied }" source="复制的内容">
<button @click="copy()">
<!-- 建议优化为复制相关的图标 -->
{{ copied ? '复制成功' : '复制' }}
</button>
</UseClipboard>
</template>
获取联网状态 UseNetwork / UseOnline
html
<script setup>
import { UseNetwork } from '@vueuse/components'
</script>
<template>
<UseNetwork v-slot="{ isOnline }"> 是否联网: {{ isOnline }} </UseNetwork>
</template>
另一个也类似
html
<script setup>
import { UseOnline } from '@vueuse/components'
</script>
<template>
<UseOnline v-slot="{ isOnline }"> 是否联网: {{ isOnline }} </UseOnline>
</template>
更多组件可参考官网,持续更新中!