skilld-dev/vue-ecosystem-skills

tanstack-vue-virtual-skilld

Headless UI for virtualizing scrollable elements in Vue. ALWAYS use when writing code importing \"@tanstack/vue-virtual\". Consult for debugging, best practices, or modifying @tanstack/vue-virtual, tanstack/vue-virtual, tanstack vue-virtual, tanstack vue virtual, virtual.

First seen Feb 19, 2026

Installation

$ npx skills add skilld-dev/vue-ecosystem-skills --skill tanstack-vue-virtual-skilld

Similar popular skills

Related neighbors and high-traction skills in the same topics — useful to compare before installing.

Also in this package

Other skills from skilld-dev/vue-ecosystem-skills · top by installs.

npx skills add skilld-dev/vue-ecosystem-skills

Browse all from skilld-dev/vue-ecosystem-skills

More details

Agent compatibility

Declared targets from SKILL.md / docs. Unmarked agents are not listed — the skill may still install via the CLI.

Claude Code Not declared
Cursor Not declared
Codex Not declared
GitHub Copilot Not declared
Windsurf Not declared
Gemini CLI Not declared
Cline Not declared
OpenCode Not declared

Repository health

Stars 179
License LICENSE
Default branch main
Open issues 2
Status Active

Skill metadata

Parsed from SKILL.md frontmatter.

Version3.13.24
More metadata
version
3.13.24
generated_at
2026-04-18
references_synced_at
2026-04-18

Package contents

Files included with this skill beyond the listing page.

  • skill md SKILL.md 6,960 B
  • docs SUMMARY.md 307 B

History

  1. First seen on skills.sh
  2. First recorded snapshot · 119 installs

SKILL.md

TanStack/virtual @tanstack/[email protected]

Tags: beta: 3.0.0-beta.68, latest: 3.13.24

References: [Docs](./references/docs/_INDEX.md)

API Changes

This section documents version-specific API changes — prioritize recent major/minor releases.

  • BREAKING: useVirtualizer — replaces useVirtual in v3 migration; older positional arguments or v2 option names are no longer supported [source](./references/docs/framework/vue/vue-virtual.md)
  • BREAKING: Ref<Virtualizer> return type — v3 useVirtualizer returns a Vue Ref instead of a raw object; instance methods must be accessed via .value (e.g., rowVirtualizer.value.getVirtualItems())
  • BREAKING: count — replaces size option in v3 migration; using size will result in zero items being virtualized [source](./references/docs/api/virtualizer.md)
  • BREAKING: getScrollElement — replaces parentRef option in v3 migration; must be a function that returns the scrollable element or null [source](./references/docs/api/virtualizer.md)
  • BREAKING: measureElement — replaces measureRef pattern from v2; you must now pass virtualizer.value.measureElement to the ref attribute and set data-index on the element [source](./references/docs/api/virtualizer.md)
  • NEW: getTotalSize() auto-updates — as of v3.13.13, the virtualizer automatically notifies the framework when the count option changes, ensuring getTotalSize() and the UI update correctly without manual workarounds for filtering or search [source](./references/releases/@tanstack/[email protected])
  • NEW: lanes — new in v3; allows dividing the list into multiple columns (vertical) or rows (horizontal) to support grid-like or masonry layouts [source](./references/docs/api/virtualizer.md)
  • NEW: gap — new in v3; specifies the spacing between items in pixels, removing the need for manual margin or padding calculations [source](./references/docs/api/virtualizer.md)
  • NEW: useWindowVirtualizer — specialized adapter for window-based scrolling; simplifies configuration when the browser window is the scroll container [source](./references/docs/framework/vue/vue-virtual.md)
  • NEW: scrollMargin — allows specifying the offset between the scroll container's start and the beginning of the virtualized list; essential for lists preceded by headers [source](./references/docs/api/virtualizer.md)
  • NEW: isRtl — built-in support for right-to-left language locales; inverts horizontal scrolling logic when enabled [source](./references/docs/api/virtualizer.md)
  • NEW: useScrollendEvent — utilizes the native scrollend event where available to reset isScrolling state, falling back to a debounced timer if disabled [source](./references/docs/api/virtualizer.md)
  • NEW: shouldAdjustScrollPositionOnItemSizeChange — provides fine-grained control over scroll position adjustments when dynamic items differ from their estimated size [source](./references/docs/api/virtualizer.md)
  • NEW: useAnimationFrameWithResizeObserver — added in v3.13.x; defers ResizeObserver measurement processing to the next animation frame to batch DOM mutations [source](./references/docs/api/virtualizer.md)

Also changed: isScrollingResetDelay new in v3 · rangeExtractor now receives Range object · VirtualItem adds lane property · resizeItem method for manual size overrides · enabled option to pause observers

Best Practices

  • Account for scrollMargin in absolute positioning — when using a shared scroll container with static headers, subtract the margin from the item's start position to maintain correct layout [source](./references/docs/api/virtualizer.md)
<script setup>
const rowVirtualizer = useVirtualizer({
  count: 1000,
  scrollMargin: 100, // Height of header
  // ...
})
</script>

<template>
  <div v-for="item in rowVirtualizer.getVirtualItems()" :key="item.key"
    :style="{
      transform: `translateY(${item.start - rowVirtualizer.options.scrollMargin}px)`
    }"
  >
    {{ item.index }}
  </div>
</template>
  • Overestimate estimateSize for dynamic elements — providing a "maximum likely" size prevents the scrollbar from jumping and items from "resetting" their position when scrolling upwards into unmeasured territory [source](./references/docs/api/virtualizer.md)
  • Implement shouldAdjustScrollPositionOnItemSizeChange for chat/messaging UIs — use this callback to control scroll adjustments when prepending items, preventing visual jumps as new elements are measured [source](./references/docs/api/virtualizer.md)
  • Attach data-index when using measureElement — the virtualizer requires this attribute on the measured DOM element to correctly map the size back to the item's internal state [source](./references/docs/api/virtualizer.md)
<div
  v-for="item in virtualizer.getVirtualItems()"
  :key="item.key"
  :data-index="item.index"
  :ref="virtualizer.measureElement"
>
  {{ item.index }}
</div>
  • Pass configuration via computed or Ref — the Vue adapter's useVirtualizer watch-triggers setOptions automatically, allowing the instance to reactively update count or overscan without manual re-instantiation
  • Avoid useAnimationFrameWithResizeObserver for performance — native ResizeObserver is already batched; enabling this adds a ~16ms delay that can cause visual flickering or stale measurements during fast scrolls [source](./references/docs/api/virtualizer.md)
  • Provide a stable getItemKey for persistent state — using a unique identifier (like a database ID) instead of the default index ensures that item state (focus, internal refs) is preserved during reorders or filtering [source](./references/docs/api/virtualizer.md)
  • Wrap initial scrollToIndex in requestAnimationFrame — for "scroll-to-bottom" initialization (e.g. chat), deferring the scroll ensures the DOM is rendered and initial measurements are processed by the virtualizer [source](./references/discussions/discussion-911.md)
  • Use built-in gap over manual CSS margins — the gap option ensures the virtualizer accounts for item spacing in its internal getTotalSize() calculation, which manual margins do not [source](./references/docs/api/virtualizer.md)
  • Pause observers with enabled: false — instead of unmounting the virtualizer, toggle the enabled option to pause monitoring (e.g., when a tab is hidden). This preserves existing measurements while saving CPU cycles [source](./references/docs/api/virtualizer.md)