Merge pull request #5120 from tsiegleauq/nav-from-motion-blocks
Add navigation flag to return to custom oriring
This commit is contained in:
commit
ed8d666fce
@ -17,6 +17,11 @@ export class RoutingStateService {
|
|||||||
*/
|
*/
|
||||||
private _previousUrl: string;
|
private _previousUrl: string;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Stores the routing state
|
||||||
|
*/
|
||||||
|
private _customOrigin: string;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Unsafe paths that the user should not go "back" to
|
* Unsafe paths that the user should not go "back" to
|
||||||
* TODO: Might also work using Routing parameters
|
* TODO: Might also work using Routing parameters
|
||||||
@ -39,6 +44,10 @@ export class RoutingStateService {
|
|||||||
return this._previousUrl;
|
return this._previousUrl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public get customOrigin(): string {
|
||||||
|
return this._customOrigin;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Watch routing changes and save the last visited URL
|
* Watch routing changes and save the last visited URL
|
||||||
*
|
*
|
||||||
@ -52,10 +61,33 @@ export class RoutingStateService {
|
|||||||
)
|
)
|
||||||
.subscribe((event: any[]) => {
|
.subscribe((event: any[]) => {
|
||||||
this._previousUrl = event[0].urlAfterRedirects;
|
this._previousUrl = event[0].urlAfterRedirects;
|
||||||
|
if (
|
||||||
|
this.router.getCurrentNavigation().extras &&
|
||||||
|
this.router.getCurrentNavigation().extras.state &&
|
||||||
|
this.router.getCurrentNavigation().extras.state.back
|
||||||
|
) {
|
||||||
|
this._customOrigin = this._previousUrl;
|
||||||
|
} else if (
|
||||||
|
this._customOrigin &&
|
||||||
|
!this.isSameComponent(event[0].urlAfterRedirects, event[1].urlAfterRedirects)
|
||||||
|
) {
|
||||||
|
this._customOrigin = null;
|
||||||
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public goBack(): void {
|
public goBack(): void {
|
||||||
this.location.back();
|
this.location.back();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Analyse the URL to check if you were navigating using the same components
|
||||||
|
*/
|
||||||
|
private isSameComponent(urlA: string, urlB: string): boolean {
|
||||||
|
const pathA = urlA.slice(0, urlA.lastIndexOf('/'));
|
||||||
|
const pathB = urlB.slice(0, urlB.lastIndexOf('/'));
|
||||||
|
const paramA = urlA.slice(urlA.lastIndexOf('/') + 1);
|
||||||
|
const paramB = urlB.slice(urlA.lastIndexOf('/') + 1);
|
||||||
|
return pathA === pathB && !isNaN(+paramA) && !isNaN(+paramB);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -222,6 +222,8 @@ export class HeadBarComponent implements OnInit {
|
|||||||
public onBackButton(): void {
|
public onBackButton(): void {
|
||||||
if (this.goBack) {
|
if (this.goBack) {
|
||||||
this.routingState.goBack();
|
this.routingState.goBack();
|
||||||
|
} else if (this.routingState.customOrigin && this.routingState.customOrigin !== this.router.url) {
|
||||||
|
this.router.navigate([this.routingState.customOrigin], { relativeTo: this.route });
|
||||||
} else {
|
} else {
|
||||||
this.router.navigate([this.prevUrl], { relativeTo: this.route });
|
this.router.navigate([this.prevUrl], { relativeTo: this.route });
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
<os-head-bar [nav]="false" [multiSelectMode]="isMultiSelect" goBack="true">
|
<os-head-bar prevUrl="../.." [nav]="false" [multiSelectMode]="isMultiSelect">
|
||||||
<!-- Title -->
|
<!-- Title -->
|
||||||
<div class="title-slot" *ngIf="!parentMotion"><h2 translate>Amendments</h2></div>
|
<div class="title-slot" *ngIf="!parentMotion"><h2 translate>Amendments</h2></div>
|
||||||
|
|
||||||
@ -38,7 +38,7 @@
|
|||||||
>
|
>
|
||||||
<!-- Meta -->
|
<!-- Meta -->
|
||||||
<div *pblNgridCellDef="'meta'; row as motion" class="cell-slot fill">
|
<div *pblNgridCellDef="'meta'; row as motion" class="cell-slot fill">
|
||||||
<a class="detail-link" [routerLink]="motion.getDetailStateURL()"></a>
|
<a class="detail-link" [routerLink]="motion.getDetailStateURL()" [state]="{ back: 'true' }"></a>
|
||||||
<div class="innerTable">
|
<div class="innerTable">
|
||||||
<!-- Identifier and line -->
|
<!-- Identifier and line -->
|
||||||
<div class="title-line one-line">
|
<div class="title-line one-line">
|
||||||
|
@ -55,7 +55,7 @@
|
|||||||
<ng-container matColumnDef="anchor">
|
<ng-container matColumnDef="anchor">
|
||||||
<mat-header-cell *matHeaderCellDef></mat-header-cell>
|
<mat-header-cell *matHeaderCellDef></mat-header-cell>
|
||||||
<mat-cell *matCellDef="let motion">
|
<mat-cell *matCellDef="let motion">
|
||||||
<a [routerLink]="motion.getDetailStateURL()"></a>
|
<a [routerLink]="motion.getDetailStateURL()" [state]="{ back: 'true' }"></a>
|
||||||
</mat-cell>
|
</mat-cell>
|
||||||
</ng-container>
|
</ng-container>
|
||||||
|
|
||||||
|
@ -40,7 +40,12 @@
|
|||||||
>
|
>
|
||||||
<!-- Title column -->
|
<!-- Title column -->
|
||||||
<div *pblNgridCellDef="'title'; row as motion; rowContext as rowContext" class="cell-slot fill">
|
<div *pblNgridCellDef="'title'; row as motion; rowContext as rowContext" class="cell-slot fill">
|
||||||
<a class="detail-link" [routerLink]="motion.getDetailStateURL()" *ngIf="!isMultiSelect"></a>
|
<a
|
||||||
|
class="detail-link"
|
||||||
|
[routerLink]="motion.getDetailStateURL()"
|
||||||
|
[state]="{ back: 'true' }"
|
||||||
|
*ngIf="!isMultiSelect"
|
||||||
|
></a>
|
||||||
<div class="column-title innerTable">
|
<div class="column-title innerTable">
|
||||||
<div class="title-line ellipsis-overflow">
|
<div class="title-line ellipsis-overflow">
|
||||||
<!-- Is Favorite -->
|
<!-- Is Favorite -->
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
<os-head-bar
|
<os-head-bar
|
||||||
[hasMainButton]="perms.isAllowed('can_create_amendments', motion)"
|
[hasMainButton]="perms.isAllowed('can_create_amendments', motion)"
|
||||||
mainActionTooltip="New amendment"
|
mainActionTooltip="New amendment"
|
||||||
[prevUrl]="getPrevUrl()"
|
prevUrl="../.."
|
||||||
[nav]="false"
|
[nav]="false"
|
||||||
[editMode]="editMotion"
|
[editMode]="editMotion"
|
||||||
[isSaveButtonEnabled]="contentForm.valid"
|
[isSaveButtonEnabled]="contentForm.valid"
|
||||||
@ -144,9 +144,12 @@
|
|||||||
<span *ngIf="showSequential && motion.parent_id">· </span>
|
<span *ngIf="showSequential && motion.parent_id">· </span>
|
||||||
<span *ngIf="motion.parent_id">
|
<span *ngIf="motion.parent_id">
|
||||||
<span>
|
<span>
|
||||||
<span translate>Amendment to</span> <a [routerLink]="motion.parent.getDetailStateURL()">{{
|
<span translate>Amendment to</span> <a
|
||||||
motion.parent.identifier || motion.parent.title
|
[routerLink]="motion.parent.getDetailStateURL()"
|
||||||
}}</a>
|
[state]="{ back: 'true' }"
|
||||||
|
>
|
||||||
|
{{ motion.parent.identifier || motion.parent.title }}
|
||||||
|
</a>
|
||||||
</span>
|
</span>
|
||||||
</span>
|
</span>
|
||||||
</span>
|
</span>
|
||||||
@ -440,7 +443,7 @@
|
|||||||
<!-- Ammendments -->
|
<!-- Ammendments -->
|
||||||
<div *ngIf="!editMotion && amendments && amendments.length > 0">
|
<div *ngIf="!editMotion && amendments && amendments.length > 0">
|
||||||
<h4 translate>Amendments</h4>
|
<h4 translate>Amendments</h4>
|
||||||
<a [routerLink]="['/motions/amendments', motion.id]">
|
<a [routerLink]="['/motions/amendments', motion.id]" [state]="{ back: 'true' }">
|
||||||
{{ amendments.length }}
|
{{ amendments.length }}
|
||||||
<span *ngIf="amendments.length === 1" translate>Amendment</span>
|
<span *ngIf="amendments.length === 1" translate>Amendment</span>
|
||||||
<span *ngIf="amendments.length > 1" translate>Amendments</span>
|
<span *ngIf="amendments.length > 1" translate>Amendments</span>
|
||||||
@ -621,12 +624,7 @@
|
|||||||
<!-- Title -->
|
<!-- Title -->
|
||||||
<div *ngIf="editMotion" class="content-field form-title">
|
<div *ngIf="editMotion" class="content-field form-title">
|
||||||
<mat-form-field *ngIf="editMotion">
|
<mat-form-field *ngIf="editMotion">
|
||||||
<input
|
<input matInput placeholder="{{ 'Title' | translate }}" formControlName="title" required />
|
||||||
matInput
|
|
||||||
placeholder="{{ 'Title' | translate }}"
|
|
||||||
formControlName="title"
|
|
||||||
required
|
|
||||||
/>
|
|
||||||
<mat-error>{{ 'The title is required' | translate }}</mat-error>
|
<mat-error>{{ 'The title is required' | translate }}</mat-error>
|
||||||
</mat-form-field>
|
</mat-form-field>
|
||||||
</div>
|
</div>
|
||||||
@ -839,11 +837,7 @@
|
|||||||
<div class="content-field" *ngIf="editMotion">
|
<div class="content-field" *ngIf="editMotion">
|
||||||
<div *ngIf="perms.isAllowed('change_metadata', motion)">
|
<div *ngIf="perms.isAllowed('change_metadata', motion)">
|
||||||
<mat-form-field>
|
<mat-form-field>
|
||||||
<input
|
<input matInput placeholder="{{ 'Origin' | translate }}" formControlName="origin" />
|
||||||
matInput
|
|
||||||
placeholder="{{ 'Origin' | translate }}"
|
|
||||||
formControlName="origin"
|
|
||||||
/>
|
|
||||||
</mat-form-field>
|
</mat-form-field>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
@ -35,7 +35,6 @@ import { DiffLinesInParagraph, LineRange } from 'app/core/ui-services/diff.servi
|
|||||||
import { LinenumberingService } from 'app/core/ui-services/linenumbering.service';
|
import { LinenumberingService } from 'app/core/ui-services/linenumbering.service';
|
||||||
import { PersonalNoteService } from 'app/core/ui-services/personal-note.service';
|
import { PersonalNoteService } from 'app/core/ui-services/personal-note.service';
|
||||||
import { PromptService } from 'app/core/ui-services/prompt.service';
|
import { PromptService } from 'app/core/ui-services/prompt.service';
|
||||||
import { RoutingStateService } from 'app/core/ui-services/routing-state.service';
|
|
||||||
import { ViewportService } from 'app/core/ui-services/viewport.service';
|
import { ViewportService } from 'app/core/ui-services/viewport.service';
|
||||||
import { Mediafile } from 'app/shared/models/mediafiles/mediafile';
|
import { Mediafile } from 'app/shared/models/mediafiles/mediafile';
|
||||||
import { Motion } from 'app/shared/models/motions/motion';
|
import { Motion } from 'app/shared/models/motions/motion';
|
||||||
@ -451,7 +450,6 @@ export class MotionDetailComponent extends BaseViewComponent implements OnInit,
|
|||||||
private itemRepo: ItemRepositoryService,
|
private itemRepo: ItemRepositoryService,
|
||||||
private motionSortService: MotionSortListService,
|
private motionSortService: MotionSortListService,
|
||||||
private motionFilterService: MotionFilterListService,
|
private motionFilterService: MotionFilterListService,
|
||||||
private routingStateService: RoutingStateService,
|
|
||||||
private cd: ChangeDetectorRef
|
private cd: ChangeDetectorRef
|
||||||
) {
|
) {
|
||||||
super(title, translate, matSnackBar);
|
super(title, translate, matSnackBar);
|
||||||
@ -1538,30 +1536,6 @@ export class MotionDetailComponent extends BaseViewComponent implements OnInit,
|
|||||||
this.raiseError(error);
|
this.raiseError(error);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Tries to determine the previous URL if it's considered unsafe
|
|
||||||
*
|
|
||||||
* @returns the target to navigate to
|
|
||||||
*/
|
|
||||||
public getPrevUrl(): string {
|
|
||||||
if (this.motion && this.motion.parent_id) {
|
|
||||||
if (this.routingStateService.previousUrl && this.routingStateService.isSafePrevUrl) {
|
|
||||||
if (
|
|
||||||
(this.previousMotion &&
|
|
||||||
this.routingStateService.previousUrl === this.previousMotion.getDetailStateURL()) ||
|
|
||||||
(this.nextMotion && this.routingStateService.previousUrl === this.nextMotion.getDetailStateURL())
|
|
||||||
) {
|
|
||||||
return '../..';
|
|
||||||
} else {
|
|
||||||
return this.routingStateService.previousUrl;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
return this.motion.parent.getDetailStateURL();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return '../..';
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function to prevent automatically closing the window/tab,
|
* Function to prevent automatically closing the window/tab,
|
||||||
* if the user is editing a motion.
|
* if the user is editing a motion.
|
||||||
|
Loading…
Reference in New Issue
Block a user