@vueuse/components 15.0.0
Renderless component and directive wrappers around @vueuse/core composables. 46 components, 14 directives, 2 deprecated directive aliases (dist/index.js:1237).
Facts (all citations are paths inside the prepared @vueuse/components package):
- Version 15.0.0 (package.json:4); depends on
@vueuse/core15.0.0 and@vueuse/shared15.0.0 (package.json:43-44) - Peer dependency:
vue^3.5.0(package.json:40) - Node.js
>=22(package.json:37); Node 20 support was dropped in v15 - ESM-only (
"type": "module", package.json:3); no CJS build sideEffects: false, tree-shakeable (package.json:22); IIFE bundle exposed for CDN viaunpkg/jsdelivr(package.json:30-31)- Install:
npm i @vueuse/components @vueuse/core(README.md:10, https://vueuse.org/guide/components)
How the components work
Two families, decided by what they render (verified in dist/index.js):
- Pure renderless: no DOM of their own, render only the default slot, scoped slot receives the reactive composable return. Example
UseMouse(dist/index.js:805-809). - Element wrapper: render one element (
props.as || "div") whose ref feeds the composable, slot content becomes children. The element is the composable's target. ExampleUseElementBounding(dist/index.js:340-345).
Element-wrapper components: OnClickOutside, OnLongPress, UseDraggable, UseElementBounding, UseElementOverflow, UseElementSize, UseElementVisibility, UseFullscreen, UseImage (renders img when no default slot), UseMouseInElement, UseMousePressed, UsePointerLock, UseScreenSafeArea, UseVirtualList (own container/wrapper divs).
All others are pure renderless. Full catalog with props, slot data, and emits: references/components.md.
Common tasks
Mouse position (official guide pattern, https://vueuse.org/guide/components):
<template>
<UseMouse v-slot="{ x, y }">
x: {{ x }} y: {{ y }}
</UseMouse>
</template>
Dark mode toggle; note UseDark slot data is { isDark, toggleDark } (dist/index.js:173-178):
<template>
<UseDark v-slot="{ isDark, toggleDark }">
<button @click="toggleDark()">Is Dark: {{ isDark }}</button>
</UseDark>
</template>
Outside click, component style. OnClickOutside takes an options prop and emits trigger; the rendered div is the target (dist/index.js:5-17):
<OnClickOutside :options="{ ignore: [ignoreElRef] }" @trigger="close">
<div>Click outside of me</div>
</OnClickOutside>
Directive style, with the [handler, options] tuple binding (dist/index.js:26-29):
<script setup>
import { vOnClickOutside } from '@vueuse/components'
</script>
<template>
<div v-if="modal" v-on-click-outside="[closeModal, { ignore: [ignoreElRef] }]">
Hello World
</div>
</template>
Image with loading and error slots (dist/index.js:763-770):
<UseImage src="https://place.dog/300/200">
<template #loading>Loading..</template>
<template #error>Failed</template>
</UseImage>
Draggable with persisted position; storage-key enables useStorage persistence, storage-type picks local (default) or session (dist/index.d.ts:157-168, dist/index.js:286-300):
<UseDraggable storage-key="panel-pos" :initial-value="{ x: 10, y: 10 }" v-slot="{ x, y, style }">
<div :style="style">Drag me at {{ x }}, {{ y }}</div>
</UseDraggable>
Rules to apply
- Import components and directives as named exports from
@vueuse/components. There is noapp.use()plugin; register globally yourself if needed (app.component('UseMouse', UseMouse)). - In
On*components, pass configuration through theoptionsprop and react through the@triggeremit, not through handler props (dist/index.js:15-16, 66-68). - On element-wrapper components, set
asto change the rendered element, e.g.as="section"(dist/index.js:11). Exception:UseScreenSafeAreatypes declareasbut its runtime props array omits it, so it always renders adiv(dist/index.js:1096-1101 vs dist/index.d.ts:548-553). UseIdlerequires thetimeoutprop (dist/index.d.ts:297-299).UseVirtualListrequireslistandoptionsprops;heightdefaults to300px; it exposesscrollTo(index)via template ref (dist/index.d.ts:590-610, dist/index.js:1190-1206).UseObjectUrlrenders its slot only after the object URL exists; slot prop is the URL string (dist/index.js:906-915).UseOffsetPaginationemitspage-change,page-size-change,page-count-changewith the full pagination state (dist/index.js:918-951).UsePointeracceptstarget="window"(default) ortarget="self"(dist/index.d.ts:463-465, dist/index.js:976-984).- Do not use the deprecated exports
VOnClickOutsideandVOnLongPress; they aliasvOnClickOutside/vOnLongPress(dist/index.d.ts:17-18, 43-44). - Directive binding values: a handler function, or a
[handler, options]tuple;vElementSizetakes[handler, initialSize, options]andvScrollLocktakes a boolean. Details and modifiers: references/directives.md.
References
- references/components.md — catalog of all 46 components: props, slot data shapes, emits, rendered element
- references/directives.md — all 14 directives: binding value forms, modifiers, handler payloads
- references/migration.md — version-specific changes v13 to v15 with official release URLs
Official documentation: https://vueuse.org/guide/components