How to highlight active menu item with Typescript and Vue.js 3?

Viewed 25

I have a menu and would like to highlight the currently active menu item.
I think I should write in the first template the following: v-if(selected) and some function maybe.

<template>
  <MenuTreeView @selected='collapsedMenuSelected' :items='filteredFirstLevelNavigation' :filter="false"/>
</template>

MenuTreeView:

<template>
  <Tree :value="items" filterPlaceholder="Suche" :expandedKeys="expandedKeys" filterMode="lenient" :filter="filter"
        selectionMode="single" @nodeSelect="onNodeSelect"></Tree>
</template>
1 Answers

In such cases, you need to store the id of the active element in the data of the parent component. This can be done by saving the id when selecting one of the rows.
Parent

<template>
  <div class="menu">
    <MenuItem
      v-for="row in rows"
      :active-id="activeId"
      :key="row.id"
      @select="handleSelect"
    />
  </div>
</template>

<script>
import MenuItem from "./MenuItem";
export default {
  name: "TheMenu",
  components: {
    MenuItem,
  },
  data() {
    return {
      activeId: null,
      rows: [
        {
          id: 1,
          label: "First",
        },
        {
          id: 2,
          label: "Second",
        },
        {
          id: 3,
          label: "Third",
        },
      ],
    };
  },
  methods: {
    handleSelect(id) {
      this.activeId = id;
    },
  },
};
</script>

Child

<template>
  <div
    class="menu-item"
    :class="{
      'menu-item_active': activeId === row.id,
    }"
    @click="handleSelect"
  >
    {{ row.label }}
  </div>
</template>

<script>
export default {
  name: "MenuItem",
  props: {
    row: {
      type: Object,
      required: true,
    },
    activeId: {
      type: Number,
      required: true,
    },
  },
  methods: {
    handleSelect() {
      this.$emit("select", this.row.id);
    },
  },
};
</script>

<!-- Add "scoped" attribute to limit CSS to this component only -->
<style scoped>
.menu-item {
  /* your styles */
  display: flex;
  width: 100%;
}
.menu-item_active {
  background-color: red;
}
</style>

Related