Skip to main content
Vuetify0 is now a release candidate!
Vuetify0 Logo
Theme
Mode
Palettes
Accessibility
Vuetify One
Sign in to Vuetify One

Access premium tools across the Vuetify ecosystem — Bin, Play, Studio, and more.

Not a subscriber? See what's included

Rating

Headless rating input with hover preview, keyboard navigation, and half-step support.

Usage

Rating supports whole and half-star modes. Items expose their state via data attributes for CSS-only styling.

Rating: 0

<script setup lang="ts">
  import { Rating } from '@vuetify/v0'
  import { shallowRef } from 'vue'

  const rating = shallowRef(0)
</script>

<template>
  <div class="flex flex-col items-center gap-4">
    <Rating.Root v-slot="{ attrs }" v-model="rating" class="flex gap-1 focus:outline-none" renderless>
      <div v-bind="attrs" class="flex gap-0.5">
        <Rating.Item
          v-for="i in 5"
          :key="i"
          as="button"
          class="size-8 text-xl cursor-pointer focus:outline-none [&[data-state=full]]:text-amber-500 [&[data-state=empty]]:text-on-surface-variant/40"
          :index="i"
        >
          <template #default="{ state }">
            {{ state === 'full' ? '★' : '☆' }}
          </template>
        </Rating.Item>
      </div>
    </Rating.Root>

    <p class="text-sm text-on-surface-variant">
      Rating: {{ rating }}
    </p>
  </div>
</template>

Anatomy

vue
<script setup lang="ts">
  import { Rating } from '@vuetify/v0'
</script>

<template>
  <Rating.Root>
    <Rating.Item />
    <Rating.HiddenInput />
  </Rating.Root>
</template>

Examples

Product review form

A “leave a review” widget that pairs a half-star Rating.Root with a validated comment field inside a single Form. The rating runs in renderless mode, so the slot attrs (which carry role="slider" plus the aria-value* and keyboard bundle) bind to your own wrapper element, and each Rating.Item renders a star from its state slot prop — layering a clipped filled star over an outline for the "half" state. The half prop unlocks 0.5-step precision, and a live label translates the hovered or committed value (“Good”, “Excellent”) so the reader always sees what they are about to submit.

Form submission is where the two controls diverge. The comment is an Input field, so it auto-registers with the Form validation registry and the @submit payload’s valid flag already reflects its rules. The rating is not a validation field, so it cannot ride that flag — the component keeps a local starsError and only forwards a successful submit when both the Form is valid and a rating was chosen. The name="review-rating" prop on Rating.Root auto-renders the hidden input, so the star value posts with the form without ever placing a Rating.HiddenInput by hand.

Reach for this triad when a rating is one part of a larger form rather than a standalone control: the composable owns the submitted-review state and reset, the reusable component owns the v0 surface and styling, and the entry wires them together with a summary panel. The trade-off is the manual rating-required guard — acceptable here because mixing a slider-style control with text validation in one submit is a common real-world shape. Related: createRating, Slider.

FileRole
useReview.tsOwns the review state (stars, comment, submitted) plus submit/reset behavior
ReviewForm.vueRenders the Rating + Input inside a Form and guards the rating-required rule
review-form.vueWires the composable to the form and shows the submitted-review summary
Your rating
Tap to rate

Stars feed the name="review-rating" hidden input; the review text validates through the Form before submission.

Accessibility

Keyboard

KeyAction
ArrowRight / ArrowUpIncrement by step (1 or 0.5)
ArrowLeft / ArrowDownDecrement by step
HomeSet to 0
EndSet to size

ARIA

Rating.Root provides role="slider" with aria-valuenow, aria-valuemin, aria-valuemax, and aria-valuetext (e.g. “3 out of 5”). When disabled or readonly, the corresponding aria-disabled and aria-readonly attributes are set.

Data Attributes

Root:

AttributeDescription
data-disabledPresent when disabled
data-readonlyPresent when readonly
data-hoveringPresent during hover

Item:

AttributeValuesDescription
data-statefull | half | emptyFill state
data-highlightedpresent/absentWithin hover range
data-disabledpresent/absentInherited from root
data-readonlypresent/absentInherited from root

FAQ

Discord
Need help? Join our community for support and discussions ↗

API Reference

The following API details are for all variations of the Rating component.
Was this page helpful?

Ctrl+/