vuetify.js

Vuetify: Button dropdown with multiple selections (checkboxes)


I want a button that opens a dropdown list with multiple items that are selectable. Another way to see it is that I want a v-select component with the multiple property, but replacing the v-select input field with a button.

I have seen a working example here. However, when I try to re-create it using the latest Vuetify version, it does not work as expected, as the v-select input is showing. How can I solve this? :)

Code (Playground link):

<template>
  <v-app>
    <v-container>
      <v-btn
        @click="toggleSelect = !toggleSelect"
        :color="`${toggleSelect ? 'primary':'none'}`"
      >
        Open
      </v-btn>
      <v-select
        :items="items"
        multiple
        item-title="text"
        item-value="value"
        v-if="toggleSelect"
        v-model="selectedItems"
        :menu-props="{value: toggleSelect}"
        return-object
        hide-details
      ></v-select>

      <br />
      {{ selectedItemsTitles }}
    </v-container>
  </v-app>
</template>

<script setup>
  import { computed, ref, watch } from 'vue'

  const toggleSelect = ref(false)
  const selectedItems = ref([])
  const selectedItemsTitles = computed(() =>
    selectedItems.value.map(i => i.text).join(', ')
  )
  const items = [
    { text: 'Dessert (100g serving)', value: 'name' },
    { text: 'Calories', value: 'calories' },
    { text: 'Fat (g)', value: 'fat' },
  ]
</script>

Solution

  • VSelect uses VMenu under the hood, you can pass props to it through VSelect's :menu-props. VMenu can be configured to open on button click by passing a template ref to the :activator prop and setting :open-on-click to true. This will open the menu below the button when you click it.

    Finally, you can hide the v-text-field from the v-select by a plain CSS display:none or by setting v-show="false" (make sure Vue still renders the VSelect, otherwise the v-menu will be gone too).

    <v-btn ref="toggleSelectButton"> Open </v-btn>
    <v-select
      :menu-props="{
        activator: toggleSelectButton,
        openOnClick: true,
      }"
      v-show="false"
      ...
    

    and (in composition API):

    const toggleSelectButton = ref()
    

    Here it is in a playground