Categories
Vuetify

Vuetify — Menus and Context Menu

Spread the love

Vuetify is a popular UI framework for Vue apps.

In this article, we’ll look at how to work with the Vuetify framework.

Rounded

We round the menu corners with the rounded prop.

For example, we can write:

<template>
  <v-row justify="space-around">
    <v-col cols="12">
      <v-menu rounded="rounded" offset-y>
        <template v-slot:activator="{ attrs, on }">
          <v-btn color="primary" class="white--text ma-8" v-bind="attrs" v-on="on">Menu</v-btn>
        </template>

        <v-list>
          <v-list-item v-for="item in items" :key="item.title" link>
            <v-list-item-title v-text="item.title"></v-list-item-title>
          </v-list-item>
        </v-list>
      </v-menu>
    </v-col>
  </v-row>
</template>
<script>
export default {
  name: "HelloWorld",
  data: () => ({
    items: [
      { title: "Click Me" },
      { title: "Click Me 2" },
      { title: "Click Me 3" },
    ],
  }),
};
</script>

We set the rounded prop to rounded so that we can have a big menu.

Close on Click

Menus can be closed when focus is lost.

For example, we can write:

<template>
  <v-row justify="space-around">
    <v-col cols="12">
      <v-menu close-on-click>
        <template v-slot:activator="{ attrs, on }">
          <v-btn color="primary" class="white--text ma-8" v-bind="attrs" v-on="on">Menu</v-btn>
        </template>

        <v-list>
          <v-list-item v-for="item in items" :key="item.title" link>
            <v-list-item-title v-text="item.title"></v-list-item-title>
          </v-list-item>
        </v-list>
      </v-menu>
    </v-col>
  </v-row>
</template>
<script>
export default {
  name: "HelloWorld",
  data: () => ({
    items: [
      { title: "Click Me" },
      { title: "Click Me 2" },
      { title: "Click Me 3" },
    ],
  }),
};
</script>

The close-on-click will make the menu close on click.

Absolute Position without Activator

We can place our menu with absolute position without a component to trigger it.

For example, we can write:

<template>
  <v-row justify="space-around">
    <v-col cols="12">
      <div>
        <v-row class="flex" justify="center">
          <v-card
            :ripple="false"
            class="portrait"
            img="https://placekitten.com/600/600"
            height="300px"
            width="300px"
            @contextmenu="show"
          ></v-card>
        </v-row>

<v-menu v-model="showMenu" :position-x="x" :position-y="y" absolute offset-y>
          <v-list>
            <v-list-item v-for="(item, index) in items" :key="index">
              <v-list-item-title>{{ item.title }}</v-list-item-title>
            </v-list-item>
          </v-list>
        </v-menu>
      </div>
    </v-col>
  </v-row>
</template>
<script>
export default {
  name: "HelloWorld",
  data: () => ({
    showMenu: false,
    x: 0,
    y: 0,
    items: [
      { title: "Click Me" },
      { title: "Click Me 2" },
      { title: "Click Me 3" },
    ],
  }),
  methods: {
    show(e) {
      e.preventDefault();
      this.showMenu = false;
      this.x = e.clientX;
      this.y = e.clientY;
      this.$nextTick(() => {
        this.showMenu = true;
      });
    },
  },
};
</script>

We have the card that has the contextmenu event listener to listen to right clicks.

When we right-click on the card, the show method is run.

We set the showMenu state to false to clear the existing menu.

And set the x and y states are set so that we positon the menu to where the right click is done.

We set x and y to the position-x and position-y props to set the menu position.

Also, we need the absolute prop to make the menu position in absolute position.

Conclusion

We can make the menu rounded and create a context menu with Vuetify.

By John Au-Yeung

Web developer specializing in React, Vue, and front end development.

Leave a Reply

Your email address will not be published. Required fields are marked *