Bob
Bob

Reputation: 619

Hide elements based on routing in Angular2 rc1

I have some elements I want on every page except the login page. I'd like to use ngIf or possibly the hidden property of the elements to hide those elements when the user is on the login page.

I have tried this:

<div [hidden]="router.isRouteActive(router.generate('/login'))">

based on this question and answer: In Angular 2 how do you determine the active route?

And have also tried this:

 <div *ngIf="!router.isRouteActive(router.generate('/login'))">

but haven't had any success.

For reference here is the component that matches this html.

import { Component, OnInit } from 'node_modules/@angular/core';
import { HTTP_PROVIDERS, XHRBackend } from 'node_modules/@angular/http';
import { Routes, Router, ROUTER_DIRECTIVES } from 'node_modules/@angular/router';

import { LoginService } from './login/login.service';
import { LoginComponent } from './login/login.component';
import { UserComponent } from './user/user.component';

@Component({
    selector: 'portal',
    templateUrl: 'portal/portal.component.html',
    directives: [ROUTER_DIRECTIVES, LoginComponent, UserComponent ],
    providers: [
        HTTP_PROVIDERS,
        LoginService
    ]
})

@Routes([
    { path: '/login', component: LoginComponent},
    { path: '/user/:username', component: UserComponent}
])

export class PortalComponent implements OnInit{
    private router: Router
    constructor() {}

    ngOnInit() {
        this.router.navigate(['/login']); 
    } 
}

The documentation for isRouteActive is pretty slim, the same for generate. Any direction on a better way to achieve this behavior?

Upvotes: 27

Views: 49245

Answers (11)

David Diomede
David Diomede

Reputation: 81

Based off of @Michelangelo's Comment:

In Your Component:

import { Routes, Router } from 'node_modules/@angular/router';

export class YourComponent implements OnInit{
     constructor(public router: Router ) {
    }
}

In HTML:

<ng-container *ngIf="!router.url.includes('admin')">
    <p>The content you want to hide when in the above url path</p>
</ng-container>

Upvotes: 2

Axel186
Axel186

Reputation: 561

RxJS example (Observable):

@Component({
  ...
})
export class AppComponent{
    hideElement$: Observable<boolean> = this.router.events
        .pipe(
            filter((event) => event instanceof NavigationEnd),
            map((data: any) => data.url === '/login')
        );
}
<ng-container *ngIf="!(hideElement$ | async)">
  <p>Hide me on Login page!</p>
</ng-container>

Upvotes: 2

Mangesh Daundkar
Mangesh Daundkar

Reputation: 1046

You can hide/show elements by checking the url for specific component,

Modify your component.ts file like this,

import { RouterModule, Router, NavigationEnd } from '@angular/router';

hideElement = false;

constructor(private router: Router) {
  this.router.events.subscribe((event) => {
    if (event instanceof NavigationEnd) {
      if (event.url === '/login') {
        this.hideElement = true;
      }  else {
        this.hideElement = false;
      }
    }
  });
}

Use this hideElement property in component.html

<div [hidden]="hideElement">

Upvotes: 9

maxbellec
maxbellec

Reputation: 17491

Simply check the router.url in the template:

my.component.ts

...
constructor(public router: Router){}
...

my.component.html

<div *ngIf="router.url != '/login'">
    <h2>Not in login!</h2>
</div>

Upvotes: 46

marcus hall
marcus hall

Reputation: 566

At least with more recent versions of angular 2 and depending on the specific use case.You can transclude the content and only add it on the route component where you want it. Much better than maintaining a list of routes and using ngIf conditions.

In your component template. Add an ngcontent element and use select to give it a name

<ng-content select="[content-name]"></ng-content>  

Then you can use that component and transclude the content.

<component>
<div content-name> transcluded content</div>
</component>

Or use it without referencing the transcluded content

<component>
</component>

Upvotes: 1

admax
admax

Reputation: 1671

There is a hack we can use in some simple cases. It is based on RouterLinkActive directive that can be added not only to anchors but to it's parents also. So we can do the following:

<div routerLinkActive="hidden">
    <a routerLink="/login">Login</a>
</div>

hidden is a standard bootstrap class:

.hidden {
    display: none!important;
}

How it works: when you are inside login area, the hidden class is added and you do not see the div. Once you navigate to another route, the hidden class disappears and the div is visible.

The drawback is that you require to have a link with routerLink inside the div.

Upvotes: 5

Michelangelo
Michelangelo

Reputation: 5948

All of the solutions did not work out as expected. If you have route with parameters. You can use ES6 includes:

<div *ngIf="!_router.url.includes('login')">Show me except on login page</div>

Upvotes: 7

Aswin Gopalan
Aswin Gopalan

Reputation: 201

This is what I did for Angular2 RC5 router :

import {Router} from '@angular/router';

public location = '' ;

constructor(private  _router : Router) 
{      
  this.location = _router.url;
}

In HTML :

<div *ngIf = "location == '/home' ">
</div>

Hope this helps !

Upvotes: 20

hartpdx
hartpdx

Reputation: 2340

I had to do something similar in my code. I did this programmatically by creating the list of routes I wanted to exclude my element from showing in.

In my class, I injected the Location object from @angular/common.

public isHidden() {
  let list = ["/login"],
      route = this.location.path();

  return (list.indexOf(route) > -1);
}

Then in my template, I use the hidden attribute and bind it to my function.

<div id="elementToHide" [hidden]="isHidden()"></div>

Upvotes: 7

Bob
Bob

Reputation: 619

I was able to find the syntax I needed for rc1 buried in a comment here: In Angular 2 how do you determine the active route?

<div *ngIf="!router.urlTree.contains(router.createUrlTree(['/login']))">

Upvotes: 15

Picci
Picci

Reputation: 17762

I would try router.generate(['/login']) rather than router.generate('/login').

This syntax sometimes is tricky.

I hope this helps in your case

Upvotes: -3

Related Questions