I have the following tab structure in my page, with it's respective URLs given in braces:
Main Tab (/page)
/ | \
/ | \
/ | \
/ | \
Sub Tab 1 Sub Tab 2 Sub Tab 3
(/page/a) (/page/b) (/page/c)
Component
@Input() route: string = '';
selectTab(tab) {
let route = this.router.url.split('?')[0];
/* Here redirectUrl = "/page/c" */
if (tab.redirectUrl.length > 0) {
// console.log(tab.redirectUr); gives /page/c
this.router.navigate([tab.redirectUrl]);
// This works but reloads the page and is a very bad idea.
// window.location.href = tab.redirectUrl;
}
}
Component.html
NOTE: The actual code has a custom element, I'm showing it as a <div>
just to show how redirectUrl
is passed.
<div route="/page" [redirectUrl]="/page/c"></div>
The selectTab
function is called when I click Main Tab. And since the Main Tab has redirectUrl
the if condition satisfies and the page goes from /page
to /page/c
. (This only works once)
But, if I click any other Sub Tab (say Sub Tab 2
with URL /page/b
), then clicking on main tab doesn't redirect to /page/c
, instead stays at /page/b
.
I have already checked the redirectUrl
inside if condition, it's still /page/c
, but redirection doesn't happen.
What should I do to force redirection?
EDIT
@HuseinRoncevic
<div *ngFor="let tab of tabs" (click)="selectTab(tab)">
EDIT
Routes
{
path: 'page',
component: MyComponent
},
{
path: 'page/:action',
component: MyComponent
}
I am not sure why your route definition points to the same component:
{
path: 'page',
component: MyComponent
},
{
path: 'page/:action',
component: MyComponent
}
Why don't you create a separate component for page/:action
route?
Here is something from the Routing and Navigation documentation on Angular.io.
Observable paramMap and component reuse
In this example, you retrieve the route parameter map from an Observable. That implies that the route parameter map can change during the lifetime of this component.
They might. By default, the router re-uses a component instance when it re-navigates to the same component type without visiting a different component first. The route parameters could change each time.
I believe that this is your issue. You are not really changing the components. Rather, you are reusing the same component over and over again. And for that reason router is reusing the same component instance.
For that reason I would create a new component that handles the :action
part of your route.
{
path: 'page',
component: MyComponent
},
{
path: 'page/:action',
component: IHandleActionPartHereComponent
}
Update
In your selectTab()
function, what is the purpose of splitting along the question mark?
let route = this.router.url.split('?')[0];
Your route will not be appended as a query parameter, but rather it will be appended to the actual route as in http://something/page/a
not http://something/?page/b
or however you imagined this. The url
property will return the url as determined by the router: /page/a
or /page/b
. The length of your result should be 0. Because of that your if
part will always be false and no redirection will occur.
You can try this:
{ path: 'page', component: PageParentComponent,
children: [
{ path: '', redirectTo: 'a', pathMatch: 'full'},
{ path: 'a', component: AComponent},
{ path: 'b', component: BComponent}
]
}
in HTML
this.router.navigate(['page/a']); // or
this.router.navigate(['page/b']);