Vue-router: Support for activeStyle and exactActiveStyle

Created on 9 Feb 2019  路  9Comments  路  Source: vuejs/vue-router

What problem does this feature solve?

Coming from React and using React Router, there is support for activeStyle property. Like activeClass but a style object of styles to apply to an element when active. This helps for things like theming where the theme color is plucked from store and needs to be applied to an element when active.

What does the proposed API look like?

takes a prop activeStyle and exactActiveStyle, both type object, works identically to activeClass and exactActiveClass

feature request group[router-link redesign]

Most helpful comment

All 9 comments

I'm marking this as a feature request but the final api may completely different as the new scoped slots api allows us to retrieve state from router-link, so it could be used like this:

<router-link v-slot="{ isActive }" :style=" isActive && styleActive" exact>link</router-link>

That being said I also see value in a prop

@posva that could work, just having to do some really hacky stuff at the moment and anything that router-link could provide to make this more seamless would be great :)

Couldn't we have something like:

<router-link to="/" slot-scope="{ isActive, isExactActive }" :class="{ 'bg-blue': isActive }">
  Home
</router-link>

I'm using Tailwind CSS and this would really help. Is it possible with the current slot-scope syntax?

that's pretty much what I wrote but with a class, yeah

Having access to that info through a slot scope would be awesome 馃檶馃徎 The biggest pain point I have with the current API is that I can't add classes only to _inactive_ links, which means I have to include those styles on all links, and then actively undo/override those when the link is active.

@posva Right, sorry, read too fast!

@adamwathan Did you try a selector like a:not(.router-link-active):not(.router-link-exact-active) instead?

Yeah that would work! In my case I'm trying to avoid writing complex selectors like that and instead just applying existing utilities so what I've done for now is just compare the current route to the route I'm linking to manually:

<li class="mb-3 lg:mb-1" v-for="[link, title] in section.children">
  <router-link :to="link" v-if="$route.path === link" class="px-2 -mx-2 py-1 transition-fast relative block text-teal-600 font-medium">
    <span class="rounded absolute inset-0 bg-teal-200 opacity-25"></span>
    <span class="relative">{{ title }}</span>
  </router-link>

  <router-link :to="link" v-else class="px-2 -mx-2 py-1 transition-fast relative block hover:translate-r-2px hover:text-gray-900 text-gray-600 font-medium">
    <span class="rounded absolute inset-0 bg-teal-200 opacity-0"></span>
    <span class="relative">{{ title }}</span>
  </router-link>
</li>

Not as robust but fine for my situation.

Given the current v-slot api, adding a style when the route is active can be achieved like this:

<router-link v-slot="{ isActive, href, navigate }">
  <a :href="href" @click="navigate"  :style=" isActive && styleActive" >My Link</router-link>
</router-link>

There is already active-class and exact-active-class to directly change the applied classes. I doesn't seem like most users are interested in changing the style directly and since it's achievable in user land by wrapping the router-link, we are closing this

Was this page helpful?
0 / 5 - 0 ratings