Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Disable a component on some routes? #254

Closed
joedawson opened this issue Nov 25, 2015 · 11 comments
Closed

Disable a component on some routes? #254

joedawson opened this issue Nov 25, 2015 · 11 comments

Comments

@joedawson
Copy link

Hello,

I'm not sure if this the correct way of thinking - but I want one of my components to be disabled or deactivated on some routes.

So here's my routes.

router.map({
    '/':                        { component: ProductsView },
    '/auth/login':              { component: LoginView },
    '/auth/register':           { component: RegisterView },
    '/products':                { component: ProductsView },
    '/products/:product':       { component: ProductView },
    '/categories':              { component: CategoriesView },
    '/categories/:category':    { component: CategoryView },
    '*':                        { component: NotFoundView }
});

My main template file looks like so:

<!DOCTYPE html>
<html lang="en" id="app">
    <head>
        <!-- Head Contents -->
    </head>
    <body>
        <header>
            <!-- Header Contents -->
            <navigation></navigation>
        </header>
        <div class="container">
            <router-view></router-view>
        </div>
    </body>
</html>

When I'm on either the /auth/login or /auth/register routes - I do not want my navigation component to appear.

How can I achieve this?

@amirrustam
Copy link

@joedawson I'm sure Vue provides many mechanisms to accomplish this. I believe the v-if or v-show directives should be used since this is a conditional rendering matter.

Now for the conditional expression to use with those directives you can utilize the $route.path or $route.name which are made available to each component by vue-router. This is documented here: http://vuejs.github.io/vue-router/en/route.html

First I would add names to my routes:

router.map({
    // ...
    '/auth/login': { name: 'login', component: LoginView },
    '/auth/register':  { name: 'register', component: RegisterView },
   // ...
});

Then you can just conditionally display the navigation based on the current route name:

<navigation v-if="['login', 'register'].indexOf($route.name) > -1"></navigation>

This is just one way, and I'm sure it can be cleaned up a bit. Though I would like to know if there is a potential best practice way to do this since I imagine this is a common pattern.
Maybe @yyx990803 can enlighten us on the matter.

@joedawson
Copy link
Author

@amirrustam I approached it a little differently in the end - I simply added a class to the body if the current route matched either /auth/login or /auth/register then used CSS to hide the component. Not the best solution I guess, but a working one.

<body :class="{ 'auth': $route.path==='/auth/register' || $route.path==='/auth/login' }">

@ricky11
Copy link

ricky11 commented Jun 18, 2018

Cool. is their a best practice to this, i couldn't find anything in the vue cookbook.

@sandersu
Copy link

This will also work

<navigation v-if="['login', 'register'].includes($route.name)"></navigation>

@GNSubrahmanyam
Copy link

What are the best practices for hiding/disabling a component on some routes?

@hudhaifas
Copy link

In the nav component listen to the route changes to update a flag whether the nav will be shown or hidden, you may check with route name or path:

note: the following example uses typescript:

export const router = new Router({
  mode: "history",
  routes: [
    { name: "home", path: "/", component: Home },
    { name: "login", path: "/login", component: LoginView }
  ]
});
<nav v-if="showHeader">
...
</nav>
  @Watch("$route", { immediate: true })
  OnRouteChange(route: Route) {
    if (route.name == "login" || route.name == "signup") {
      this.showHeader = false;
    } else {
      this.showHeader = true;
    }
  }

@moody
Copy link

moody commented Jun 17, 2019

Route meta fields provide yet another option:

const router = new VueRouter({
  routes: [
    {
      path: '/foo',
      component: Foo,
      meta: { hideNavigation: true }
    }
  ]
})
<navigation v-if="!$route.meta.hideNavigation" />

@titusdecali
Copy link

This question covers a useful thing to know in general, however if you want to show/hide certain main components like a header or footer, the best way is to simply create multiple layouts that include the components you want.

@vishalvaghasiya
Copy link

vishalvaghasiya commented Feb 15, 2020

Hide Header in some components using the current route path.

get current route path using this.$route.path

<navigation v-if="showNavigation"></navigation>
data() {
this.$route.path === '/' ? this.showNavigation = false : this.showNavigation = true
}

@Kashish-2001
Copy link

How can we achieve this in nuxt?

@jmcazura
Copy link

For someone don't want to use v-if and v-show you can use named views.
https://router.vuejs.org/guide/essentials/named-views.html

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests