Skip to content

Commit 0e9a6ae

Browse files
ADjenkovADjenkov
ADjenkov
authored and
ADjenkov
committed
feat(location-strategy): introduce path property to Outlet. Match the path to Outlet when search in the UrlTree for the given Outlet
1 parent 71471f5 commit 0e9a6ae

File tree

2 files changed

+42
-17
lines changed

2 files changed

+42
-17
lines changed

Diff for: nativescript-angular/router/ns-location-strategy.ts

+40-15
Original file line numberDiff line numberDiff line change
@@ -15,18 +15,24 @@ export class Outlet {
1515
// More than one key available when using NSEmptyOutletComponent component
1616
// in module that lazy loads children (loadChildren) and has outlet name.
1717
outletKeys: Array<string>;
18+
19+
// The url path to the Outlet.
20+
// E.G: the path to Outlet3 that is nested Outlet1(home)->Outlet2(nested1)->Outlet3(nested2)
21+
// will be 'home/nested1'
22+
path: string;
1823
pathByOutlets: string;
1924
states: Array<LocationState> = [];
2025
frame: Frame;
2126

2227
// Used in reuse-strategy by its children to determine if they should be detached too.
2328
shouldDetach: boolean = true;
24-
constructor(outletKey: string, pathByOutlets: string, modalNavigationDepth?: number) {
29+
constructor(outletKey: string, path: string, pathByOutlets: string, modalNavigationDepth?: number) {
2530
this.outletKeys = [outletKey];
2631
this.isPageNavigationBack = false;
2732
this.showingModal = false;
2833
this.modalNavigationDepth = modalNavigationDepth || 0;
2934
this.pathByOutlets = pathByOutlets;
35+
this.path = path;
3036
}
3137

3238
peekState(): LocationState {
@@ -88,7 +94,7 @@ export class NSLocationStrategy extends LocationStrategy {
8894
}
8995

9096
let tree = this.currentUrlTree;
91-
let changedOutlet = this.getSegmentGroup(this.currentOutlet.pathByOutlets);
97+
let changedOutlet = this.getSegmentGroupByOutlet(this.currentOutlet);
9298

9399
// Handle case where the user declares a component at path "/".
94100
// The url serializer doesn't parse this url as having a primary outlet.
@@ -130,13 +136,13 @@ export class NSLocationStrategy extends LocationStrategy {
130136
// The url serializer doesn't parse this url as having a primary outlet.
131137
if (!Object.keys(urlTreeRoot.children).length) {
132138
const segmentGroup = this.currentUrlTree && this.currentUrlTree.root;
133-
const outletKey = this.getSegmentGroupFullPath(segmentGroup) + "primary";
139+
const outletKey = this.getOutletKey(this.getSegmentGroupFullPath(segmentGroup), "primary");
134140
const outlet = this.findOutletByKey(outletKey);
135141

136142
if (outlet && this.updateStates(outlet, segmentGroup)) {
137143
this.currentOutlet = outlet; // If states updated
138144
} else if (!outlet) {
139-
const rootOutlet = this.createOutlet("primary", segmentGroup, null);
145+
const rootOutlet = this.createOutlet("primary", null, segmentGroup, null);
140146
this.currentOutlet = rootOutlet;
141147
}
142148

@@ -153,16 +159,19 @@ export class NSLocationStrategy extends LocationStrategy {
153159
currentSegmentGroup.outlet = outletName;
154160
currentSegmentGroup.root = urlTreeRoot;
155161

156-
let outletKey = this.getSegmentGroupFullPath(currentTree) + outletName;
162+
const outletPath = this.getSegmentGroupFullPath(currentTree);
163+
let outletKey = this.getOutletKey(outletPath, outletName);
157164
let outlet = this.findOutletByKey(outletKey);
165+
158166
const parentOutletName = currentTree.outlet || "";
159-
const parentOutletKey = this.getSegmentGroupFullPath(currentTree.parent) + parentOutletName;
167+
const parentOutletPath = this.getSegmentGroupFullPath(currentTree.parent);
168+
const parentOutletKey = this.getOutletKey(parentOutletPath, parentOutletName);
160169
const parentOutlet = this.findOutletByKey(parentOutletKey);
161170

162171
const containsLastState = outlet && outlet.containsTopState(currentSegmentGroup.toString());
163172
if (!outlet) {
164173
// tslint:disable-next-line:max-line-length
165-
outlet = this.createOutlet(outletKey, currentSegmentGroup, parentOutlet, this._modalNavigationDepth);
174+
outlet = this.createOutlet(outletKey, outletPath, currentSegmentGroup, parentOutlet, this._modalNavigationDepth);
166175
this.currentOutlet = outlet;
167176
} else if (this._modalNavigationDepth > 0 && outlet.showingModal && !containsLastState) {
168177
// Navigation inside modal view.
@@ -270,7 +279,7 @@ export class NSLocationStrategy extends LocationStrategy {
270279
private callPopState(state: LocationState, pop: boolean = true, outlet?: Outlet) {
271280
outlet = outlet || this.currentOutlet;
272281
const urlSerializer = new DefaultUrlSerializer();
273-
let changedOutlet = this.getSegmentGroup(outlet.pathByOutlets);
282+
let changedOutlet = this.getSegmentGroupByOutlet(outlet);
274283

275284
if (state && changedOutlet) {
276285
this.updateSegmentGroup(this.currentUrlTree.root, changedOutlet, state.segmentGroup);
@@ -469,7 +478,7 @@ export class NSLocationStrategy extends LocationStrategy {
469478
currentRoute = currentRoute.parent;
470479
}
471480

472-
return fullPath ? fullPath + outletName : outletName;
481+
return fullPath ? fullPath + "-" + outletName : outletName;
473482
}
474483

475484

@@ -568,9 +577,10 @@ export class NSLocationStrategy extends LocationStrategy {
568577
}
569578
}
570579

571-
private createOutlet(outletKey: string, segmentGroup: any, parent: Outlet, modalNavigation?: number): Outlet {
580+
// tslint:disable-next-line:max-line-length
581+
private createOutlet(outletKey: string, path: string, segmentGroup: any, parent: Outlet, modalNavigation?: number): Outlet {
572582
const pathByOutlets = this.getPathByOutlets(segmentGroup);
573-
const newOutlet = new Outlet(outletKey, pathByOutlets, modalNavigation);
583+
const newOutlet = new Outlet(outletKey, path, pathByOutlets, modalNavigation);
574584

575585
const locationState: LocationState = {
576586
segmentGroup: segmentGroup,
@@ -590,15 +600,18 @@ export class NSLocationStrategy extends LocationStrategy {
590600
return newOutlet;
591601
}
592602

593-
private getSegmentGroup(pathByOutlets: string): UrlSegmentGroup {
594-
const pathList = pathByOutlets.split("-");
603+
private getSegmentGroupByOutlet(outlet: Outlet): UrlSegmentGroup {
604+
const pathList = outlet.pathByOutlets.split("-");
595605
let segmentGroup = this.currentUrlTree.root;
606+
let pathToOutlet;
596607

597608
for (let index = 0; index < pathList.length; index++) {
598609
const currentPath = pathList[index];
599610
const childrenCount = Object.keys(segmentGroup.children).length;
600611

601612
if (childrenCount && segmentGroup.children[currentPath]) {
613+
const url = segmentGroup.toString();
614+
pathToOutlet = pathToOutlet ? pathToOutlet + "/" + url : url;
602615
segmentGroup = segmentGroup.children[currentPath];
603616
} else {
604617
// If no child outlet found with the given name - forget about all previously found outlets.
@@ -609,6 +622,12 @@ export class NSLocationStrategy extends LocationStrategy {
609622
}
610623
}
611624

625+
// Paths should also match since there could be another Outlet
626+
// with the same pathByOutlets but different url path.
627+
if (segmentGroup && outlet.path && pathToOutlet && outlet.path !== pathToOutlet) {
628+
segmentGroup = null;
629+
}
630+
612631
return segmentGroup;
613632
}
614633

@@ -645,11 +664,17 @@ export class NSLocationStrategy extends LocationStrategy {
645664

646665
// No currentModalOutlet available when opening 'primary' p-r-o.
647666
const outletName = "primary";
648-
const outletKey = parentOutlet.peekState().segmentGroup.toString() + outletName;
649-
currentModalOutlet = this.createOutlet(outletKey, segmentedGroup, parentOutlet, this._modalNavigationDepth);
667+
const outletPath = parentOutlet.peekState().segmentGroup.toString();
668+
const outletKey = this.getOutletKey(outletPath, outletName);
669+
// tslint:disable-next-line:max-line-length
670+
currentModalOutlet = this.createOutlet(outletKey, outletPath, segmentedGroup, parentOutlet, this._modalNavigationDepth);
650671
this.currentOutlet = currentModalOutlet;
651672
} else if (this.updateStates(currentModalOutlet, segmentedGroup)) {
652673
this.currentOutlet = currentModalOutlet; // If states updated
653674
}
654675
}
676+
677+
private getOutletKey(path: string, outletName: string): string {
678+
return path ? path + "-" + outletName : outletName;
679+
}
655680
}

Diff for: tests/app/tests/modal-dialog.ts

+2-2
Original file line numberDiff line numberDiff line change
@@ -93,7 +93,7 @@ describe("modal-dialog", () => {
9393
.then((fixture: ComponentFixture<SuccessComponent>) => {
9494
const service = <ModalDialogService>fixture.componentRef.instance.service;
9595
const locStrategy = <NSLocationStrategy>fixture.componentRef.instance.locationStrategy;
96-
const outlet = new Outlet("primary", "primary", 0);
96+
const outlet = new Outlet("primary", null, "primary", 0);
9797

9898
let parentView = fixture.componentRef.instance.vcRef.element.nativeElement;
9999
parentView = parentView.page && parentView.page.frame;
@@ -115,7 +115,7 @@ describe("modal-dialog", () => {
115115
.then((fixture: ComponentFixture<SuccessComponent>) => {
116116
const service = <ModalDialogService>fixture.componentRef.instance.service;
117117
const locStrategy = <NSLocationStrategy>fixture.componentRef.instance.locationStrategy;
118-
const outlet = new Outlet("primary", "primary", 0);
118+
const outlet = new Outlet("primary", null, "primary", 0);
119119

120120
let parentView = fixture.componentRef.instance.vcRef.element.nativeElement;
121121
parentView = parentView.page && parentView.page.frame;

0 commit comments

Comments
 (0)