2016-10-24 8 views
1

ユーザーが特定のページを表示しているときに自動的にナビゲーションを非表示にしようとしています。たとえば、ユーザーがログインページを表示している場合、メニューは表示されません。ルートに基づく特定のページの角2の非表示のナビゲーション

私が今まで試したことは、現在のページのURLパスに基づいて「ショーナビゲーション」フラグを変更するNavigatorサービスがあることです。これはApp Guardによってアクセスされます。そのジョブは、次のURLをNavigatorサービスに渡し、 "show navigation"フラグを更新することです。

これまでのテストでは、クリックイベントを介してビューを更新して、サービスが正しいデータを受け取り、それに応じて更新していることを確認しています。

私が持っている唯一の問題は、「show navigation」フラグの「すべての時間」の変更を購読/聞く方法を考えることができないことです。私が意味することは、ナビゲーションを隠して自動的に表示したいということです。

ナビゲーターサービス

import { Injectable } from '@angular/core'; 

import { Observable } from 'rxjs/Observable'; 

@Injectable() 
export class NavigatorService { 
    private showNavigation: boolean = false; 

    displayNavigation(): Observable<boolean> { 
     return Observable.of(this.showNavigation); 
    } 

    toggleNavigation(urlPath: string) { 
     if (urlPath === 'login') { 
      this.showNavigation = false; 
     } else { 
      this.showNavigation = true; 
     } 
    } 
} 

のAppガード

import { Injectable } from '@angular/core'; 
import { ActivatedRouteSnapshot, CanActivate } from '@angular/router'; 

import { Observable } from 'rxjs/Observable'; 

import { NavigatorService } from '../services'; 

@Injectable() 
export class AppGuard implements CanActivate { 
    constructor(private navigatorService: NavigatorService) { } 

    canActivate(next: ActivatedRouteSnapshot) { 
     console.log(next); 

     this.navigatorService.toggleNavigation(next.url[0].path); 

     // for now returning Observable of true... 
     // will be changed when extra functionality is added 
     return Observable.of(true); 
    } 
} 

アプリケーションコンポーネント

import { Component } from '@angular/core'; 

import { NavigatorService } from './shared'; 


@Component({ 
    selector: 'app', 
    styleUrls: [ 
     './app.style.css' 
    ], 
    template: require('./app.component.html') 
}) 
export class AppComponent { 
    showNavigation: boolean = true; 

    constructor(private navigatorService: NavigatorService) { } 

    // button click event 
    toggleNav() { 
     this.navigatorService.displayNavigation 
      .subscribe(res => this.showNavigation = res); 
    } 
} 

アプリケーションコンポーネントテンプレート私はサービスに加入できるように、私は「トグルナビゲーション」ボタンを持つテストとして、今の上で見られるように

<button (click)="toggleNav()">Toggle Navigation</button> 
<div id="page-wrapper"> 
    <div id="sidebar-wrapper" *ngIf="showNavigation"> 
     <navigation></navigation> 
    </div> 
    <div id="page-content-wrapper"> 
     <main> 
      <router-outlet></router-outlet> 
     </main> 
    </div> 
</div> 

。正直言って、これが最善の実装であるかどうかわからないし、正しい方法でこれを実行しないかもしれない。私はAppコンポーネントが何らかの形で "show navigation"フラグの値を常に意識する方法があるかどうか尋ねたいと思います。

アップデート - 問題は、私が正しく答えに私をリードし、このquestionを追ってきた

を解決しました。

ナビゲーター・サービス、私はアプリケーションコンポーネントのngOnInitライフサイクルフックにサービスに加入

import { Injectable } from '@angular/core'; 

import { Observable } from 'rxjs/Observable'; 
import { Subject } from 'rxjs/Subject'; 

@Injectable() 
export class NavigatorService { 
    private showNavigation: Subject<boolean>; 

    constructor() { 
     this.showNavigation = <Subject<boolean>>new Subject(); 
    } 

    get displayNavigation(): Observable<boolean> { 
     return this.showNavigation.asObservable(); 
    } 

    toggleNavigation(urlPath: string) { 
     let showNav: boolean; 
     if (urlPath === 'login') { 
      showNav = false; 
     } else { 
      showNav = true; 
     } 

     this.showNavigation.next(showNav); 
    } 
} 

そして:

import { Component, OnInit } from '@angular/core'; 

import { NavigatorService } from './shared'; 

@Component({ 
    selector: 'app', 
    styleUrls: [ 
     './app.style.css' 
    ], 
    template: require('./app.component.html') 
}) 
export class AppComponent implements OnInit { 
    showNavigation: boolean = true; 

    constructor(private navigatorService: NavigatorService) { } 

    ngOnInit() { 
     this.navigatorService.displayNavigation 
      .subscribe(res => this.showNavigation = res); 
    } 
} 

私はまだないんだけど、次のように私は、ナビゲーションサービスを更新しますこれが最善の方法だと100%確信していますが、これまでのところ私の問題は解決しています。

+0

ここに私の答えを見てください。あなたはそのようなものを実装することができます。 http://stackoverflow.com/questions/40213694/invoke-component-refresh-in-angular-2/40213887#40213887 – Sefa

+0

ご意見ありがとうございます。偶然にも私は問題解決のためのソリューションを使って質問を更新しました。私はこれが良い解決策であるかどうかを知るためのフィードバックをしたいと思います。 –

答えて

0

他の人の参考情報として、ルータでこれを行うことができます。下の例では、AppComponentのテンプレートに<router-outlet></router-outlet>という文字列しかありません。また、隠したいものをDefaultLayoutComponentという別のレイアウトビューに移動します。

メニュー/フッターと<router-outlet></router-outlet>をDefaultLayoutComponentに配置します。 DefaultLayoutComponentの子(つまり、以下のダッシュボードと招待コンポーネント)のみが共通のレイアウトを持つようになりました。他のページ(以下のログイン)は空白のレイアウトになります。

RouterModule.forRoot([ 
    { path: 'login', component: LoginComponent}, 
    { path: '', component: DefaultLayoutComponent, children: [ 
     { path: '', component: DashboardComponent}, 
     { path: 'dashboard', component: DashboardComponent }, 
     { path: 'invite', component: InviteComponent}] 
    }, 
    { path: '**', redirectTo: ''} 
]) 
+1

なぜダブルネストする必要がありますか? – SinistraD

+1

@SinistraD混乱するのは間違いありません!ダブルネストは必要ありません。私は混乱を避けるために自分の投稿を変更します。 –

+0

これは元の質問には答えません。これはガードがどのように使用されるかを示していません –

関連する問題