I'm trying to show the navigation bar, once the user successfully do.
For example:
How To Change "showMenu" property in "AppComponent" inside the "LoginComponent"? Important: I am using routes.
app.ts:
@Component({
selector: 'app',
template: `<div *ngIf="showMenu">
<fnd-menu-nav></fnd-menu-nav>
</div>
<router-outlet></router-outlet>
`,
directives: [ROUTER_DIRECTIVES, MenuNavComponent]
})
@RouteConfig([
{ path: '/login', name: 'Login', component: LoginComponent, useAsDefault: true },
{ path: '/welcome', name: 'Welcome', component: WelcomeComponent }
])
export class AppComponent {
public showMenu : boolean;
}
login.component.ts:
@Component({
selector: 'fnd-login',
templateUrl: './fnd/login/components/login.component.html',
providers: [LoginService]
})
export class LoginComponent {
/* .. other properties */
constructor(private _router: Router, private _loginService: LoginService ) {
}
/* .. other methods */
/* .. other methods */
private onLoginSuccessfully(data : any) : void {
/* --> HERE: Set showMenu in AppComponent to true. How? */
this._router.navigate(['Welcome']);
}
}
Or this design is not the best way to solve it?
I recently did something similar and here is how I did it. First, you need to create a NavBarComponent at the root of your app. And in the NavBarComponent you reference (what I call) a GlobalEventsManager which is a service that you inject where you need it.
Here is a look at the GlobalEventsManager:
Now you inject the GlobalEventsManger service into your login component (something like this)
Your app component then looks something like this:
Also the GlobalEventsManager must be registered when you boot the app:
That should do it.
UPDATE: I have updated this answer to reflect the more accepted way of using events outside of a component, ie in a service; which entails using BehaviorSubject/Observable instead of EventEmitter
Actually there is a totally different approach that does not use any of event emitters / listeners. I have nothing against the events and I use both approaches (the below one and @brando's one) according to the particular project needs / complexity.
The method: we have 2 application modules (areas): public (that has no navbar) and protected (the one that has one).
Public module contains all public routes:
This is what you already should have, there is nothing unusual here.
Then we have a protected area
and here the magic starts.
First of all, pay attention to the point 1:
We need this right here. If we put it to the AppModule it will be ignored. There is nothing crucial here, it might be even more logical to have this redirect in the protected module.
Point 2 allows us to proxy all the children routes into the
NavbarWrapperComponent
(point 3) which takes care of rendering of all our children. Here is a navbar component's template:This
<router-outlet>
will handle all the children routes.Possible problems you might face and their solution:
AppModule
- just change the path in the point 2 to be some real name e.g.protected
. This will prefix all of your protected urls with this value, which you might not want. You have 2 options to choose.This way might seem not that flexible, however it really works and covers nearly all the cases you might need. It does not have the events complexity and fully utilises the
Router
features. The killer thing here - it is dumb simple and very easy to understand and maintain.best modern way in angular4, with new router, with children routes, just needed use UrlSerializer-class to remove parenthesis, https://angular.io/docs/ts/latest/api/router/index/UrlSerializer-class.html, anyone did uses it?