@coolon/angular-ui-powerups 0.0.97 → 0.0.101

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (79) hide show
  1. package/bundles/coolon-angular-ui-powerups.umd.js +1405 -1305
  2. package/bundles/coolon-angular-ui-powerups.umd.js.map +1 -1
  3. package/bundles/coolon-angular-ui-powerups.umd.min.js +1 -1
  4. package/bundles/coolon-angular-ui-powerups.umd.min.js.map +1 -1
  5. package/coolon-angular-ui-powerups.d.ts +19 -19
  6. package/coolon-angular-ui-powerups.metadata.json +1 -1
  7. package/esm2015/coolon-angular-ui-powerups.js +19 -19
  8. package/esm2015/index.js +2 -2
  9. package/esm2015/lib/interaction/components/activity-container/activity-container.component.js +20 -6
  10. package/esm2015/lib/interaction/components/inplace-interaction-context/inplace-interaction-context.component.js +18 -7
  11. package/esm2015/lib/interaction/index.js +5 -4
  12. package/esm2015/lib/interaction/interaction-context.js +7 -53
  13. package/esm2015/lib/interaction/interaction.module.js +3 -3
  14. package/esm2015/lib/interaction/services/interaction.service.js +228 -0
  15. package/esm2015/lib/interaction/services/mat-dialog-interaction/dialog-interaction-context-factory.js +62 -0
  16. package/esm2015/lib/interaction/services/mat-dialog-interaction/dialog-interaction-context.js +145 -0
  17. package/esm2015/lib/interaction/services/modal-interaction-context.factory.js +17 -0
  18. package/esm2015/lib/place/components/place-outlet/place-outlet.component.js +3 -3
  19. package/esm2015/lib/place/guards/abstract-place.guard.js +13 -12
  20. package/esm2015/lib/place/guards/interaction.guard.js +27 -19
  21. package/esm2015/lib/place/guards/navigation-state.js +676 -0
  22. package/esm2015/lib/place/guards/place-component-deactivation-handler.js +14 -37
  23. package/esm2015/lib/place/index.js +2 -2
  24. package/esm2015/lib/place/place-router.js +163 -161
  25. package/esm2015/lib/place/url-snapshot.js +91 -19
  26. package/esm2015/public_api.js +3 -3
  27. package/esm5/coolon-angular-ui-powerups.js +19 -19
  28. package/esm5/index.js +2 -2
  29. package/esm5/lib/interaction/components/activity-container/activity-container.component.js +24 -15
  30. package/esm5/lib/interaction/components/inplace-interaction-context/inplace-interaction-context.component.js +15 -7
  31. package/esm5/lib/interaction/index.js +5 -4
  32. package/esm5/lib/interaction/interaction-context.js +8 -61
  33. package/esm5/lib/interaction/interaction.module.js +3 -3
  34. package/esm5/lib/interaction/services/interaction.service.js +271 -0
  35. package/esm5/lib/interaction/services/mat-dialog-interaction/dialog-interaction-context-factory.js +65 -0
  36. package/esm5/lib/interaction/services/mat-dialog-interaction/dialog-interaction-context.js +170 -0
  37. package/esm5/lib/interaction/services/modal-interaction-context.factory.js +27 -0
  38. package/esm5/lib/place/components/place-outlet/place-outlet.component.js +3 -3
  39. package/esm5/lib/place/guards/abstract-place.guard.js +15 -14
  40. package/esm5/lib/place/guards/interaction.guard.js +25 -17
  41. package/esm5/lib/place/guards/navigation-state.js +894 -0
  42. package/esm5/lib/place/guards/place-component-deactivation-handler.js +21 -55
  43. package/esm5/lib/place/index.js +2 -2
  44. package/esm5/lib/place/place-router.js +186 -269
  45. package/esm5/lib/place/url-snapshot.js +105 -21
  46. package/esm5/public_api.js +3 -3
  47. package/fesm2015/coolon-angular-ui-powerups.js +1142 -990
  48. package/fesm2015/coolon-angular-ui-powerups.js.map +1 -1
  49. package/fesm5/coolon-angular-ui-powerups.js +1350 -1250
  50. package/fesm5/coolon-angular-ui-powerups.js.map +1 -1
  51. package/lib/interaction/components/activity-container/activity-container.component.d.ts +2 -1
  52. package/lib/interaction/components/inplace-interaction-context/inplace-interaction-context.component.d.ts +3 -1
  53. package/lib/interaction/index.d.ts +4 -3
  54. package/lib/interaction/interaction-context.d.ts +2 -11
  55. package/lib/interaction/services/interaction.service.d.ts +46 -0
  56. package/lib/interaction/services/mat-dialog-interaction/dialog-interaction-context-factory.d.ts +15 -0
  57. package/lib/interaction/services/{dialog-interaction-context.d.ts → mat-dialog-interaction/dialog-interaction-context.d.ts} +2 -2
  58. package/lib/interaction/services/modal-interaction-context.factory.d.ts +4 -0
  59. package/lib/place/guards/abstract-place.guard.d.ts +1 -1
  60. package/lib/place/guards/interaction.guard.d.ts +3 -3
  61. package/lib/place/guards/navigation-state.d.ts +124 -0
  62. package/lib/place/guards/place-component-deactivation-handler.d.ts +3 -5
  63. package/lib/place/index.d.ts +1 -1
  64. package/lib/place/place-router.d.ts +17 -24
  65. package/lib/place/url-snapshot.d.ts +18 -6
  66. package/package.json +1 -1
  67. package/schematics/place-routes/templates/place-routes.ts.template +3 -3
  68. package/styles/styles.scss +1 -1
  69. package/esm2015/lib/interaction/services/dialog-interaction-context.js +0 -163
  70. package/esm2015/lib/interaction/services/dialog-interaction.service.js +0 -151
  71. package/esm2015/lib/interaction/services/modal-interaction.service.js +0 -109
  72. package/esm2015/lib/place/guards/navigation-session.js +0 -590
  73. package/esm5/lib/interaction/services/dialog-interaction-context.js +0 -188
  74. package/esm5/lib/interaction/services/dialog-interaction.service.js +0 -179
  75. package/esm5/lib/interaction/services/modal-interaction.service.js +0 -153
  76. package/esm5/lib/place/guards/navigation-session.js +0 -741
  77. package/lib/interaction/services/dialog-interaction.service.d.ts +0 -24
  78. package/lib/interaction/services/modal-interaction.service.d.ts +0 -15
  79. package/lib/place/guards/navigation-session.d.ts +0 -96
@@ -1,16 +1,15 @@
1
1
  import { DOCUMENT, CommonModule, Location } from '@angular/common';
2
2
  import { Directive, ElementRef, Inject, Input, HostListener, NgZone, NgModule, EventEmitter, Output, Component, InjectionToken, Injector, ComponentFactoryResolver, ViewContainerRef, ViewChild, ViewChildren, Injectable, ɵɵdefineInjectable, ɵɵinject, Optional, SkipSelf, HostBinding, INJECTOR } from '@angular/core';
3
3
  import { FormsModule } from '@angular/forms';
4
- import { MatInputModule, MatFormFieldModule, MatSelectModule, MatDialog, MatButtonModule, MatDialogModule, MatTabsModule as MatTabsModule$1, MatProgressSpinnerModule } from '@angular/material';
4
+ import { MatInputModule, MatFormFieldModule, MatSelectModule, MatButtonModule, MatDialogModule, MatTabsModule as MatTabsModule$1, MatProgressSpinnerModule, MatDialog } from '@angular/material';
5
5
  import { MatTabsModule } from '@angular/material/tabs';
6
6
  import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
7
- import { GarbageCollector, DelegatingValueModel, assert, UnaryCommand, lang, Dsl, Logger, DelegatingFormValueModel, UseDelegate, ValueModel, ListModel, StoreInListModel, EventListenerList, DelegatingListModel, Deferred, MutableStream, MutableValueModel, MutableListModel, Binding, Trace, Guard as Guard$1, StoreInValueModel, Command, OptionsHelper, ValueHolder } from '@coolon/pectin';
7
+ import { GarbageCollector, DelegatingValueModel, assert, UnaryCommand, lang, Dsl, Logger, DelegatingFormValueModel, UseDelegate, ValueModel, ListModel, StoreInListModel, DelegatingListModel, Deferred, MutableStream, MutableValueModel, MutableListModel, Binding, Trace, Guard, StoreInValueModel, Command, OptionsHelper, ValueHolder } from '@coolon/pectin';
8
8
  import { __decorate, __metadata, __awaiter } from 'tslib';
9
9
  import { PortalModule } from '@angular/cdk/portal';
10
- import { RouterModule, NavigationStart, NavigationCancel, NavigationEnd, UrlSegment, NavigationError, Router, UrlSerializer, ActivatedRouteSnapshot, RouterStateSnapshot } from '@angular/router';
10
+ import { RouterModule, UrlSegment, UrlSegmentGroup, NavigationStart, NavigationEnd, NavigationError, NavigationCancel, Router, UrlSerializer, ActivatedRouteSnapshot, RouterStateSnapshot } from '@angular/router';
11
11
  import ___default, { last, isNil, isEqual } from 'lodash';
12
12
  import { assert as assert$1, Opts, Klass } from '@coolon/typescript-utilities';
13
- import { MatDialogConfig, MatDialog as MatDialog$1, MAT_DIALOG_DEFAULT_OPTIONS } from '@angular/material/dialog';
14
13
  import { MatIconModule } from '@angular/material/icon';
15
14
  import { MatListModule } from '@angular/material/list';
16
15
  import { MatTooltipModule } from '@angular/material/tooltip';
@@ -19,6 +18,7 @@ import { Memoize as Memoize$1 } from '@typescript-plus/fast-memoize-decorator';
19
18
  import 'reflect-metadata';
20
19
  import { style, query, group, animate, trigger, transition } from '@angular/animations';
21
20
  import ResizeObserver from 'resize-observer-polyfill';
21
+ import { MatDialogConfig, MAT_DIALOG_DEFAULT_OPTIONS, MatDialog as MatDialog$1 } from '@angular/material/dialog';
22
22
  import { Observable } from 'rxjs';
23
23
 
24
24
  /**
@@ -896,10 +896,6 @@ if (false) {
896
896
  * @abstract
897
897
  */
898
898
  class InteractionContext extends GarbageCollector {
899
- constructor() {
900
- super(...arguments);
901
- this.activityListeners = new EventListenerList();
902
- }
903
899
  /**
904
900
  * Returns true if an activity is currently running.
905
901
  * @return {?}
@@ -908,41 +904,16 @@ class InteractionContext extends GarbageCollector {
908
904
  return this.active.value;
909
905
  }
910
906
  /**
911
- * @param {?} listener
912
- * @return {?}
913
- */
914
- addActivityListener(listener) {
915
- return this.activityListeners.add(listener);
916
- }
917
- /**
918
- * @protected
919
- * @return {?}
920
- */
921
- notifyActivityStarted() {
922
- this.activityListeners.fire((/**
923
- * @param {?} l
924
- * @return {?}
925
- */
926
- l => l.onActivityStarted()));
927
- }
928
- /**
929
- * @protected
930
907
  * @return {?}
931
908
  */
932
- notifyActivityFinished() {
933
- this.activityListeners.fire((/**
934
- * @param {?} l
935
- * @return {?}
936
- */
937
- l => l.onActivityFinished()));
909
+ dispose() {
910
+ // TODO: think about auto cancelling any outstanding activity on dispose.
911
+ // See NavigationState.Navigating for a use-case.
912
+ assert.isFalsey(this.isActive());
913
+ super.dispose();
938
914
  }
939
915
  }
940
916
  if (false) {
941
- /**
942
- * @type {?}
943
- * @private
944
- */
945
- InteractionContext.prototype.activityListeners;
946
917
  /** @type {?} */
947
918
  InteractionContext.prototype.activityList;
948
919
  /** @type {?} */
@@ -991,23 +962,6 @@ if (false) {
991
962
  */
992
963
  InteractionContext.prototype.confirmThen = function (confirm, activityType, data) { };
993
964
  }
994
- (function (InteractionContext) {
995
- /**
996
- * @record
997
- */
998
- function Listener() { }
999
- InteractionContext.Listener = Listener;
1000
- if (false) {
1001
- /**
1002
- * @return {?}
1003
- */
1004
- Listener.prototype.onActivityStarted = function () { };
1005
- /**
1006
- * @return {?}
1007
- */
1008
- Listener.prototype.onActivityFinished = function () { };
1009
- }
1010
- })(InteractionContext || (InteractionContext = {}));
1011
965
 
1012
966
  /**
1013
967
  * @fileoverview added by tsickle
@@ -1480,6 +1434,12 @@ class TabContext {
1480
1434
  this._complete = true;
1481
1435
  this.activityCallbacks.onCancel(error);
1482
1436
  }
1437
+ /**
1438
+ * @return {?}
1439
+ */
1440
+ dispose() {
1441
+ this.component.dispose();
1442
+ }
1483
1443
  }
1484
1444
  if (false) {
1485
1445
  /**
@@ -1562,9 +1522,6 @@ class ActivityContainerComponent extends InteractionContextBase {
1562
1522
  get initialActivityOutletContext() {
1563
1523
  return this._initialActivityOutletContext.value;
1564
1524
  }
1565
- // get isFinished() {
1566
- // return !this._initialActivityOutletContext;
1567
- // }
1568
1525
  /**
1569
1526
  * @return {?}
1570
1527
  */
@@ -1632,7 +1589,7 @@ class ActivityContainerComponent extends InteractionContextBase {
1632
1589
  * @return {?}
1633
1590
  */
1634
1591
  finishInitialActivity() {
1635
- this._initialActivityOutletContext = null;
1592
+ this._initialActivityOutletContext.value = null;
1636
1593
  this.initialActivityOutletContextEvent.emit(null);
1637
1594
  }
1638
1595
  // @Trace()
@@ -1651,12 +1608,23 @@ class ActivityContainerComponent extends InteractionContextBase {
1651
1608
  */
1652
1609
  cleanupStaleNestedActivities() {
1653
1610
  if (this.tabs.selectedIndex < this.activityTabs.length - 1) {
1611
+ /** @type {?} */
1612
+ const tabs = this.activityTabs.value;
1613
+ /** @type {?} */
1614
+ const remainingActivities = tabs.slice(0, 1 + this.tabs.selectedIndex);
1615
+ /** @type {?} */
1616
+ const finishedActivityTabs = tabs.slice(1 + this.tabs.selectedIndex);
1617
+ finishedActivityTabs.forEach((/**
1618
+ * @param {?} a
1619
+ * @return {?}
1620
+ */
1621
+ a => a.dispose()));
1654
1622
  this.activityTabs.runInTransaction((/**
1655
1623
  * @param {?} draft
1656
1624
  * @return {?}
1657
1625
  */
1658
1626
  draft => {
1659
- draft.value = draft.value.slice(0, 1 + this.tabs.selectedIndex);
1627
+ draft.value = remainingActivities;
1660
1628
  }));
1661
1629
  }
1662
1630
  }
@@ -1757,6 +1725,244 @@ if (false) {
1757
1725
  ActivityContainerComponent.prototype._activityList;
1758
1726
  }
1759
1727
 
1728
+ /**
1729
+ * @fileoverview added by tsickle
1730
+ * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
1731
+ */
1732
+ /**
1733
+ * @abstract
1734
+ */
1735
+ class ModalInteractionContextFactory {
1736
+ }
1737
+ if (false) {
1738
+ /**
1739
+ * @abstract
1740
+ * @return {?}
1741
+ */
1742
+ ModalInteractionContextFactory.prototype.createInteractionContext = function () { };
1743
+ }
1744
+
1745
+ /**
1746
+ * @fileoverview added by tsickle
1747
+ * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
1748
+ */
1749
+ /** @type {?} */
1750
+ let inplaceMonitorCount = 0;
1751
+ class InteractionService {
1752
+ /**
1753
+ * @param {?} modelInteractionContextFactory
1754
+ */
1755
+ constructor(modelInteractionContextFactory) {
1756
+ this.modelInteractionContextFactory = modelInteractionContextFactory;
1757
+ this.garbage = new GarbageCollector();
1758
+ this.exclusiveContext = new MutableValueModel();
1759
+ this._activeModalInteractionContextModel = new MutableValueModel();
1760
+ this._activeInlineInteractionContextModel = new MutableValueModel();
1761
+ const { chain, valueOf, before, when, after, observe, switchOn } = Dsl.disposeWith(this.garbage);
1762
+ this._activeInteractionContext = chain(this._activeModalInteractionContextModel)
1763
+ .otherwise(this._activeInlineInteractionContextModel)
1764
+ .pluck('interactionContext');
1765
+ this.active = chain(this._activeInteractionContext).isNotNil();
1766
+ this.modelInteractionActive = chain(this._activeModalInteractionContextModel).isNotNil();
1767
+ this.inlineInteractionActive = chain(this._activeInlineInteractionContextModel).isNotNil();
1768
+ // TODO: chain.concat(listOrValueModels) would be nice.
1769
+ this.activeInteractionContextIds = chain(new MutableListModel())
1770
+ .append(this._activeInlineInteractionContextModel)
1771
+ .append(this._activeModalInteractionContextModel)
1772
+ .rejectNil()
1773
+ .pluck('id');
1774
+ }
1775
+ /**
1776
+ * @return {?}
1777
+ */
1778
+ isActive() {
1779
+ return this.active.value;
1780
+ }
1781
+ /**
1782
+ * @param {?} disposable
1783
+ * @return {?}
1784
+ */
1785
+ createModalInteractionContextFor(disposable) {
1786
+ /** @type {?} */
1787
+ const context = this.modelInteractionContextFactory.createInteractionContext();
1788
+ disposable.registerDisposable(new InteractionService.Monitor('modal', context, this._activeModalInteractionContextModel, this.exclusiveContext));
1789
+ return context;
1790
+ }
1791
+ /**
1792
+ * @param {?} interactionContext
1793
+ * @return {?}
1794
+ */
1795
+ _registerInplaceInteractionContext(interactionContext) {
1796
+ interactionContext.registerDisposable(new InteractionService.Monitor(`ip${++inplaceMonitorCount}`, interactionContext, this._activeInlineInteractionContextModel, this.exclusiveContext));
1797
+ }
1798
+ /**
1799
+ * @return {?}
1800
+ */
1801
+ getCurrentActivity() {
1802
+ return __awaiter(this, void 0, void 0, function* () {
1803
+ assert$1.isTruthy(this.isActive());
1804
+ return this._activeInteractionContext.value.getCurrentActivity();
1805
+ });
1806
+ }
1807
+ /**
1808
+ * Creates an interaction context that will prevent any other contexts from starting an
1809
+ * activity until it is disposed. This is intended for use by the router for passing
1810
+ * to PlaceComponent.canDeactivate(interactionContext). This ensures components don't
1811
+ * try and interact in a way that we can't track and synchronise with the browser back
1812
+ * button.
1813
+ * @return {?}
1814
+ */
1815
+ _createExclusiveModalInteractionContext() {
1816
+ this.exclusiveContext.value = this.modelInteractionContextFactory.createInteractionContext();
1817
+ /** @type {?} */
1818
+ const self = this;
1819
+ this.exclusiveContext.value.registerDisposable({
1820
+ /**
1821
+ * @return {?}
1822
+ */
1823
+ dispose() {
1824
+ self.exclusiveContext.value = null;
1825
+ }
1826
+ });
1827
+ return this.exclusiveContext.value;
1828
+ }
1829
+ }
1830
+ InteractionService.decorators = [
1831
+ { type: Injectable, args: [{
1832
+ providedIn: 'root'
1833
+ },] }
1834
+ ];
1835
+ /** @nocollapse */
1836
+ InteractionService.ctorParameters = () => [
1837
+ { type: ModalInteractionContextFactory }
1838
+ ];
1839
+ /** @nocollapse */ InteractionService.ngInjectableDef = ɵɵdefineInjectable({ factory: function InteractionService_Factory() { return new InteractionService(ɵɵinject(ModalInteractionContextFactory)); }, token: InteractionService, providedIn: "root" });
1840
+ if (false) {
1841
+ /**
1842
+ * @type {?}
1843
+ * @private
1844
+ */
1845
+ InteractionService.prototype.garbage;
1846
+ /** @type {?} */
1847
+ InteractionService.prototype.active;
1848
+ /**
1849
+ * @type {?}
1850
+ * @private
1851
+ */
1852
+ InteractionService.prototype.exclusiveContext;
1853
+ /**
1854
+ * @type {?}
1855
+ * @private
1856
+ */
1857
+ InteractionService.prototype._activeModalInteractionContextModel;
1858
+ /**
1859
+ * @type {?}
1860
+ * @private
1861
+ */
1862
+ InteractionService.prototype._activeInlineInteractionContextModel;
1863
+ /**
1864
+ * @type {?}
1865
+ * @private
1866
+ */
1867
+ InteractionService.prototype._activeInteractionContext;
1868
+ /** @type {?} */
1869
+ InteractionService.prototype.activeInteractionContextIds;
1870
+ /** @type {?} */
1871
+ InteractionService.prototype.modelInteractionActive;
1872
+ /** @type {?} */
1873
+ InteractionService.prototype.inlineInteractionActive;
1874
+ /** @type {?} */
1875
+ InteractionService.prototype.modelInteractionContextFactory;
1876
+ }
1877
+ (function (InteractionService) {
1878
+ /**
1879
+ * @record
1880
+ */
1881
+ function Callback() { }
1882
+ InteractionService.Callback = Callback;
1883
+ if (false) {
1884
+ /**
1885
+ * @param {?} monitor
1886
+ * @return {?}
1887
+ */
1888
+ Callback.prototype.onStarted = function (monitor) { };
1889
+ /**
1890
+ * @param {?} monitor
1891
+ * @return {?}
1892
+ */
1893
+ Callback.prototype.onFinished = function (monitor) { };
1894
+ }
1895
+ class Monitor extends GarbageCollector {
1896
+ /**
1897
+ * @param {?} id
1898
+ * @param {?} interactionContext
1899
+ * @param {?} currentActiveMonitor
1900
+ * @param {?} exclusiveContext
1901
+ */
1902
+ constructor(id, interactionContext, currentActiveMonitor, exclusiveContext) {
1903
+ super();
1904
+ this.id = id;
1905
+ this.interactionContext = interactionContext;
1906
+ this.currentActiveMonitor = currentActiveMonitor;
1907
+ this.exclusiveContext = exclusiveContext;
1908
+ const { chain, valueOf, before, when, after, observe, switchOn } = Dsl.disposeWith(this);
1909
+ when.valueOf(interactionContext.active).becomesTruthy((/**
1910
+ * @return {?}
1911
+ */
1912
+ () => this.onStarted()));
1913
+ when.valueOf(interactionContext.active).becomesFalsey((/**
1914
+ * @return {?}
1915
+ */
1916
+ () => this.onFinished()));
1917
+ interactionContext.registerDisposable(this);
1918
+ }
1919
+ /**
1920
+ * @protected
1921
+ * @return {?}
1922
+ */
1923
+ onStarted() {
1924
+ this.assertCanStart();
1925
+ this.currentActiveMonitor.value = this;
1926
+ }
1927
+ /**
1928
+ * @private
1929
+ * @return {?}
1930
+ */
1931
+ assertCanStart() {
1932
+ assert$1.isFalsey(this.currentActiveMonitor.value);
1933
+ if (this.exclusiveContext.value && this.interactionContext !== this.exclusiveContext.value) {
1934
+ lang.illegalState('Interaction started while exclusive lock active. This is usually because you using a different context during place.canDeactivate(interactionContext)');
1935
+ }
1936
+ }
1937
+ /**
1938
+ * @protected
1939
+ * @return {?}
1940
+ */
1941
+ onFinished() {
1942
+ this.assertCurrentlyActive();
1943
+ this.currentActiveMonitor.value = null;
1944
+ }
1945
+ /**
1946
+ * @private
1947
+ * @return {?}
1948
+ */
1949
+ assertCurrentlyActive() {
1950
+ assert$1.isTruthy(this.currentActiveMonitor.value === this);
1951
+ }
1952
+ }
1953
+ InteractionService.Monitor = Monitor;
1954
+ if (false) {
1955
+ /** @type {?} */
1956
+ Monitor.prototype.id;
1957
+ /** @type {?} */
1958
+ Monitor.prototype.interactionContext;
1959
+ /** @type {?} */
1960
+ Monitor.prototype.currentActiveMonitor;
1961
+ /** @type {?} */
1962
+ Monitor.prototype.exclusiveContext;
1963
+ }
1964
+ })(InteractionService || (InteractionService = {}));
1965
+
1760
1966
  /**
1761
1967
  * @fileoverview added by tsickle
1762
1968
  * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
@@ -1765,17 +1971,20 @@ if (false) {
1765
1971
  * @template D, R, E
1766
1972
  */
1767
1973
  class InplaceInteractionContextComponent extends InteractionContextBase {
1768
- constructor() {
1974
+ /**
1975
+ * @param {?} interactionService
1976
+ */
1977
+ constructor(interactionService) {
1769
1978
  super();
1770
- this._active = new DelegatingValueModel().withDefault(false);
1771
- const { chain, valueOf, before, when, after, observe, switchOn } = Dsl.disposeWith(this);
1979
+ this.interactionService = interactionService;
1980
+ this._active = new MutableValueModel(false);
1981
+ this.interactionService._registerInplaceInteractionContext(this);
1772
1982
  }
1773
1983
  /**
1774
1984
  * @return {?}
1775
1985
  */
1776
1986
  ngAfterViewInit() {
1777
1987
  this.setActivityList(this.interactionContext.activityList);
1778
- this._active.setDelegate(this.interactionContext.active);
1779
1988
  }
1780
1989
  /**
1781
1990
  * @return {?}
@@ -1791,6 +2000,7 @@ class InplaceInteractionContextComponent extends InteractionContextBase {
1791
2000
  * @return {?}
1792
2001
  */
1793
2002
  _startActivity(activityType, data) {
2003
+ this._active.value = true;
1794
2004
  /** @type {?} */
1795
2005
  const self = this;
1796
2006
  return new Promise((/**
@@ -1807,6 +2017,7 @@ class InplaceInteractionContextComponent extends InteractionContextBase {
1807
2017
  * @return {?}
1808
2018
  */
1809
2019
  onDone(result) {
2020
+ self._active.value = false;
1810
2021
  resolve(result);
1811
2022
  },
1812
2023
  /**
@@ -1814,6 +2025,7 @@ class InplaceInteractionContextComponent extends InteractionContextBase {
1814
2025
  * @return {?}
1815
2026
  */
1816
2027
  onCancel(error) {
2028
+ self._active.value = false;
1817
2029
  reject(error);
1818
2030
  }
1819
2031
  };
@@ -1828,7 +2040,9 @@ InplaceInteractionContextComponent.decorators = [
1828
2040
  }] }
1829
2041
  ];
1830
2042
  /** @nocollapse */
1831
- InplaceInteractionContextComponent.ctorParameters = () => [];
2043
+ InplaceInteractionContextComponent.ctorParameters = () => [
2044
+ { type: InteractionService }
2045
+ ];
1832
2046
  InplaceInteractionContextComponent.propDecorators = {
1833
2047
  interactionContext: [{ type: ViewChild, args: ['activityContainer', { static: true },] }]
1834
2048
  };
@@ -1842,6 +2056,8 @@ if (false) {
1842
2056
  * @private
1843
2057
  */
1844
2058
  InplaceInteractionContextComponent.prototype._active;
2059
+ /** @type {?} */
2060
+ InplaceInteractionContextComponent.prototype.interactionService;
1845
2061
  }
1846
2062
 
1847
2063
  /**
@@ -1866,461 +2082,58 @@ InteractionOutletComponent.ctorParameters = () => [];
1866
2082
  * @fileoverview added by tsickle
1867
2083
  * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
1868
2084
  */
1869
- class DialogInteractionContext extends InteractionContextBase {
2085
+ class InteractionModule {
2086
+ }
2087
+ InteractionModule.decorators = [
2088
+ { type: NgModule, args: [{
2089
+ imports: [
2090
+ CommonModule,
2091
+ MatButtonModule,
2092
+ MatDialogModule,
2093
+ MatTabsModule$1,
2094
+ PortalModule,
2095
+ RouterModule
2096
+ ],
2097
+ declarations: [
2098
+ ActivityContainerComponent,
2099
+ ConfirmationDialogComponent,
2100
+ ConfirmThenDialogComponent,
2101
+ AlertDialogComponent,
2102
+ ActivityOutletComponent,
2103
+ InteractionOutletComponent,
2104
+ InplaceInteractionContextComponent
2105
+ ],
2106
+ exports: [
2107
+ ActivityContainerComponent,
2108
+ ActivityOutletComponent,
2109
+ InteractionOutletComponent,
2110
+ InplaceInteractionContextComponent
2111
+ ],
2112
+ entryComponents: [
2113
+ ActivityContainerComponent,
2114
+ ConfirmationDialogComponent,
2115
+ ConfirmThenDialogComponent,
2116
+ AlertDialogComponent
2117
+ ],
2118
+ providers: [
2119
+ InteractionService,
2120
+ ]
2121
+ },] }
2122
+ ];
2123
+
2124
+ /**
2125
+ * @fileoverview added by tsickle
2126
+ * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
2127
+ */
2128
+ /**
2129
+ * @abstract
2130
+ * @template T, E
2131
+ */
2132
+ class ParameterDefinition {
1870
2133
  /**
1871
- * @param {?} dialogService
1872
- * @param {?} config
1873
- */
1874
- constructor(dialogService, config) {
1875
- super();
1876
- this.dialogService = dialogService;
1877
- this.config = config;
1878
- this._activeModel = new MutableValueModel(false);
1879
- assert$1.notNil(dialogService);
1880
- this.onDispose((/**
1881
- * @return {?}
1882
- */
1883
- () => {
1884
- if (this.isActive()) {
1885
- lang.illegalState('Dispose called while active.');
1886
- }
1887
- }));
1888
- }
1889
- /**
1890
- * @return {?}
1891
- */
1892
- get active() {
1893
- return this._activeModel.readonly;
1894
- }
1895
- /**
1896
- * @protected
1897
- * @template D, R, E
1898
- * @param {?} activityType
1899
- * @param {?} data
1900
- * @param {?=} disableClose
1901
- * @return {?}
1902
- */
1903
- _startActivity(activityType, data, disableClose = true) {
1904
- if (this.isActive()) {
1905
- lang.illegalState(`Activity already in progress: ${this.activityList.value.map((/**
1906
- * @param {?} a
1907
- * @return {?}
1908
- */
1909
- a => a.constructor.name)).join(', ')}`);
1910
- }
1911
- this._activeModel.value = true;
1912
- this.notifyActivityStarted();
1913
- /** @type {?} */
1914
- const config = Object.assign({}, this.config, {
1915
- data,
1916
- disableClose,
1917
- panelClass: 'dialog-interaction-service'
1918
- });
1919
- /** @type {?} */
1920
- const self = this;
1921
- /** @type {?} */
1922
- const matDialogRef = (/** @type {?} */ (this.dialogService.open(ActivityContainerComponent, config)));
1923
- return new Promise((/**
1924
- * @param {?} resolve
1925
- * @param {?} reject
1926
- * @return {?}
1927
- */
1928
- (resolve, reject) => {
1929
- /** @type {?} */
1930
- const activityContainer = matDialogRef.componentInstance;
1931
- self.safelyUpdateActivityListDelegate(activityContainer.activityList);
1932
- activityContainer.initialActivityOutletContext = {
1933
- activityClass: activityType,
1934
- activityData: data,
1935
- /**
1936
- * @param {?} result
1937
- * @return {?}
1938
- */
1939
- onDone(result) {
1940
- resolve(result);
1941
- matDialogRef.close(true); // return true to let the after close listener know we've already handled it.
1942
- },
1943
- /**
1944
- * @param {?} error
1945
- * @return {?}
1946
- */
1947
- onCancel(error) {
1948
- reject(error);
1949
- matDialogRef.close(true); // return true to let the after close listener know we've already handled it.
1950
- }
1951
- };
1952
- // we need to check if our onDone/onCancel methods above we called or if we were
1953
- // closed by the user clicking the backdrop. If the later then we need to reject
1954
- // our promise.
1955
- matDialogRef.afterClosed().subscribe((/**
1956
- * @param {?} promiseAlreadyFinished
1957
- * @return {?}
1958
- */
1959
- promiseAlreadyFinished => {
1960
- if (!promiseAlreadyFinished) {
1961
- reject('auto-closed');
1962
- }
1963
- }));
1964
- matDialogRef.updateSize();
1965
- matDialogRef.afterOpened().subscribe((/**
1966
- * @param {?} promiseAlreadyFinished
1967
- * @return {?}
1968
- */
1969
- promiseAlreadyFinished => {
1970
- matDialogRef.updateSize();
1971
- }));
1972
- })).finally((/**
1973
- * @return {?}
1974
- */
1975
- () => {
1976
- this._activeModel.value = false;
1977
- this.notifyActivityFinished();
1978
- self.safelyUpdateActivityListDelegate(null);
1979
- }));
1980
- }
1981
- /**
1982
- * Updates teh delegate on the next tick to avoid modifying state during the current change detection cycle.
1983
- * @param {?} delegate
1984
- * @return {?}
1985
- */
1986
- safelyUpdateActivityListDelegate(delegate) {
1987
- setTimeout((/**
1988
- * @return {?}
1989
- */
1990
- () => this.setActivityList(delegate)));
1991
- }
1992
- }
1993
- DialogInteractionContext.decorators = [
1994
- { type: Injectable, args: [{
1995
- providedIn: 'root'
1996
- },] }
1997
- ];
1998
- /** @nocollapse */
1999
- DialogInteractionContext.ctorParameters = () => [
2000
- { type: MatDialog },
2001
- { type: MatDialogConfig }
2002
- ];
2003
- /** @nocollapse */ DialogInteractionContext.ngInjectableDef = ɵɵdefineInjectable({ factory: function DialogInteractionContext_Factory() { return new DialogInteractionContext(ɵɵinject(MatDialog$1), ɵɵinject(MatDialogConfig)); }, token: DialogInteractionContext, providedIn: "root" });
2004
- if (false) {
2005
- /**
2006
- * @type {?}
2007
- * @private
2008
- */
2009
- DialogInteractionContext.prototype._activeModel;
2010
- /**
2011
- * @type {?}
2012
- * @private
2013
- */
2014
- DialogInteractionContext.prototype.dialogService;
2015
- /** @type {?} */
2016
- DialogInteractionContext.prototype.config;
2017
- }
2018
-
2019
- /**
2020
- * @fileoverview added by tsickle
2021
- * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
2022
- */
2023
- class Guard extends ValueModel {
2024
- constructor() {
2025
- super({ initialValue: false });
2026
- }
2027
- /**
2028
- * @return {?}
2029
- */
2030
- get value() {
2031
- return this.store.read();
2032
- }
2033
- /**
2034
- * @template R
2035
- * @param {?} fun
2036
- * @return {?}
2037
- */
2038
- whileTrue(fun) {
2039
- this.startTransaction().commit(true);
2040
- try {
2041
- return fun();
2042
- }
2043
- finally {
2044
- this.startTransaction().commit(false);
2045
- }
2046
- }
2047
- /**
2048
- * @template R
2049
- * @param {?} fun
2050
- * @param {?=} defaultValue
2051
- * @return {?}
2052
- */
2053
- runIfFalse(fun, defaultValue = null) {
2054
- return !this.value ? fun() : defaultValue;
2055
- }
2056
- }
2057
- /**
2058
- * @abstract
2059
- */
2060
- class ModalInteractionService extends GarbageCollector {
2061
- constructor() {
2062
- super();
2063
- this._activityListeners = new EventListenerList();
2064
- }
2065
- /**
2066
- * @return {?}
2067
- */
2068
- isActive() {
2069
- return this.active.value;
2070
- }
2071
- /**
2072
- * @param {?} listener
2073
- * @return {?}
2074
- */
2075
- addActivityListener(listener) {
2076
- return this._activityListeners.add(listener);
2077
- }
2078
- /**
2079
- * @protected
2080
- * @return {?}
2081
- */
2082
- notifyActivityStarted() {
2083
- this._activityListeners.fire((/**
2084
- * @param {?} l
2085
- * @return {?}
2086
- */
2087
- l => l.onActivityStarted()));
2088
- }
2089
- /**
2090
- * @protected
2091
- * @return {?}
2092
- */
2093
- notifyActivityFinished() {
2094
- this._activityListeners.fire((/**
2095
- * @param {?} l
2096
- * @return {?}
2097
- */
2098
- l => l.onActivityFinished()));
2099
- }
2100
- }
2101
- if (false) {
2102
- /**
2103
- * @type {?}
2104
- * @private
2105
- */
2106
- ModalInteractionService.prototype._activityListeners;
2107
- /** @type {?} */
2108
- ModalInteractionService.prototype.active;
2109
- /**
2110
- * @abstract
2111
- * @param {?} disposable
2112
- * @return {?}
2113
- */
2114
- ModalInteractionService.prototype.createInteractionContextFor = function (disposable) { };
2115
- /**
2116
- * @abstract
2117
- * @return {?}
2118
- */
2119
- ModalInteractionService.prototype.createExclusiveInteractionContext = function () { };
2120
- /**
2121
- * @abstract
2122
- * @return {?}
2123
- */
2124
- ModalInteractionService.prototype.getCurrentActivity = function () { };
2125
- }
2126
-
2127
- /**
2128
- * @fileoverview added by tsickle
2129
- * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
2130
- */
2131
- /** @type {?} */
2132
- const DIALOG_INTERACTION_SERVICE_DEFAULTS = new InjectionToken('DIALOG_INTERACTION_SERVICE_DEFAULTS');
2133
- class DialogInteractionService extends ModalInteractionService {
2134
- /**
2135
- * @param {?} dialogService
2136
- * @param {?} dialogServiceDefaults
2137
- * @param {?} matDialogDefaultConfig
2138
- */
2139
- constructor(dialogService, dialogServiceDefaults, matDialogDefaultConfig) {
2140
- super();
2141
- this.dialogService = dialogService;
2142
- this.dialogServiceDefaults = dialogServiceDefaults;
2143
- this.matDialogDefaultConfig = matDialogDefaultConfig;
2144
- this._activeInteractionContextModel = new MutableValueModel();
2145
- assert$1.notNil(dialogService);
2146
- const { chain, valueOf, before, when, after, observe, switchOn } = Dsl.disposeWith(this);
2147
- this.active = chain(this._activeInteractionContextModel).isNotNil();
2148
- }
2149
- /**
2150
- * @param {?} disposable
2151
- * @return {?}
2152
- */
2153
- createInteractionContextFor(disposable) {
2154
- return disposable.registerDisposable(this._createInteractionContext());
2155
- }
2156
- /**
2157
- * @return {?}
2158
- */
2159
- _createInteractionContext() {
2160
- /** @type {?} */
2161
- const config = Object.assign({ autoFocus: false, hasBackdrop: true, closeOnNavigation: false }, this.matDialogDefaultConfig, this.dialogServiceDefaults);
2162
- /** @type {?} */
2163
- const self = this;
2164
- /** @type {?} */
2165
- const dialogInteractionContext = new DialogInteractionContext(this.dialogService, config);
2166
- dialogInteractionContext.registerDisposable(dialogInteractionContext.addActivityListener({
2167
- /**
2168
- * @return {?}
2169
- */
2170
- onActivityStarted() {
2171
- self.onActivityStarted(dialogInteractionContext);
2172
- },
2173
- /**
2174
- * @return {?}
2175
- */
2176
- onActivityFinished() {
2177
- self.onActivityFinished(dialogInteractionContext);
2178
- }
2179
- }));
2180
- return dialogInteractionContext;
2181
- }
2182
- /**
2183
- * @return {?}
2184
- */
2185
- createExclusiveInteractionContext() {
2186
- this.exclusiveContext = this._createInteractionContext();
2187
- /** @type {?} */
2188
- const self = this;
2189
- this.exclusiveContext.registerDisposable({
2190
- /**
2191
- * @return {?}
2192
- */
2193
- dispose() {
2194
- self.exclusiveContext = null;
2195
- }
2196
- });
2197
- return this.exclusiveContext;
2198
- }
2199
- // @Trace()
2200
- /**
2201
- * @param {?} dialogInteractionContext
2202
- * @return {?}
2203
- */
2204
- onActivityStarted(dialogInteractionContext) {
2205
- assert$1.isFalsey(this.isActive());
2206
- if (this.exclusiveContext && dialogInteractionContext !== this.exclusiveContext) {
2207
- lang.illegalState("Interaction started while exclusive lock active. This is usually because you using a different context during place.canDeactivate(interactionContext)");
2208
- }
2209
- this._activeInteractionContextModel.value = dialogInteractionContext;
2210
- this.notifyActivityStarted();
2211
- }
2212
- // @Trace()
2213
- /**
2214
- * @param {?} dialogInteractionContext
2215
- * @return {?}
2216
- */
2217
- onActivityFinished(dialogInteractionContext) {
2218
- assert$1.isTruthy(this._activeInteractionContextModel.value === dialogInteractionContext);
2219
- this._activeInteractionContextModel.value = null;
2220
- this.notifyActivityFinished();
2221
- }
2222
- /**
2223
- * @return {?}
2224
- */
2225
- getCurrentActivity() {
2226
- return __awaiter(this, void 0, void 0, function* () {
2227
- assert$1.isTruthy(this.isActive());
2228
- return this._activeInteractionContextModel.value.getCurrentActivity();
2229
- });
2230
- }
2231
- }
2232
- DialogInteractionService.decorators = [
2233
- { type: Injectable, args: [{
2234
- providedIn: 'root'
2235
- },] }
2236
- ];
2237
- /** @nocollapse */
2238
- DialogInteractionService.ctorParameters = () => [
2239
- { type: MatDialog },
2240
- { type: MatDialogConfig, decorators: [{ type: Optional }, { type: Inject, args: [DIALOG_INTERACTION_SERVICE_DEFAULTS,] }] },
2241
- { type: MatDialogConfig, decorators: [{ type: Optional }, { type: Inject, args: [MAT_DIALOG_DEFAULT_OPTIONS,] }] }
2242
- ];
2243
- /** @nocollapse */ DialogInteractionService.ngInjectableDef = ɵɵdefineInjectable({ factory: function DialogInteractionService_Factory() { return new DialogInteractionService(ɵɵinject(MatDialog$1), ɵɵinject(DIALOG_INTERACTION_SERVICE_DEFAULTS, 8), ɵɵinject(MAT_DIALOG_DEFAULT_OPTIONS, 8)); }, token: DialogInteractionService, providedIn: "root" });
2244
- if (false) {
2245
- /**
2246
- * @type {?}
2247
- * @private
2248
- */
2249
- DialogInteractionService.prototype._activeInteractionContextModel;
2250
- /** @type {?} */
2251
- DialogInteractionService.prototype.active;
2252
- /**
2253
- * @type {?}
2254
- * @private
2255
- */
2256
- DialogInteractionService.prototype.exclusiveContext;
2257
- /**
2258
- * @type {?}
2259
- * @private
2260
- */
2261
- DialogInteractionService.prototype.dialogService;
2262
- /** @type {?} */
2263
- DialogInteractionService.prototype.dialogServiceDefaults;
2264
- /** @type {?} */
2265
- DialogInteractionService.prototype.matDialogDefaultConfig;
2266
- }
2267
-
2268
- /**
2269
- * @fileoverview added by tsickle
2270
- * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
2271
- */
2272
- class InteractionModule {
2273
- }
2274
- InteractionModule.decorators = [
2275
- { type: NgModule, args: [{
2276
- imports: [
2277
- CommonModule,
2278
- MatButtonModule,
2279
- MatDialogModule,
2280
- MatTabsModule$1,
2281
- PortalModule,
2282
- RouterModule
2283
- ],
2284
- declarations: [
2285
- ActivityContainerComponent,
2286
- ConfirmationDialogComponent,
2287
- ConfirmThenDialogComponent,
2288
- AlertDialogComponent,
2289
- ActivityOutletComponent,
2290
- InteractionOutletComponent,
2291
- InplaceInteractionContextComponent
2292
- ],
2293
- exports: [
2294
- ActivityContainerComponent,
2295
- ActivityOutletComponent,
2296
- InteractionOutletComponent,
2297
- InplaceInteractionContextComponent
2298
- ],
2299
- entryComponents: [
2300
- ActivityContainerComponent,
2301
- ConfirmationDialogComponent,
2302
- ConfirmThenDialogComponent,
2303
- AlertDialogComponent
2304
- ],
2305
- providers: [
2306
- DialogInteractionService,
2307
- ]
2308
- },] }
2309
- ];
2310
-
2311
- /**
2312
- * @fileoverview added by tsickle
2313
- * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
2314
- */
2315
- /**
2316
- * @abstract
2317
- * @template T, E
2318
- */
2319
- class ParameterDefinition {
2320
- /**
2321
- * @param {?} propertyName
2322
- * @param {?} options
2323
- * @param {?=} urlFormat
2134
+ * @param {?} propertyName
2135
+ * @param {?} options
2136
+ * @param {?=} urlFormat
2324
2137
  */
2325
2138
  constructor(propertyName, options, urlFormat) {
2326
2139
  this.propertyName = propertyName;
@@ -3109,32 +2922,22 @@ class PlaceComponentDeactivationHandler {
3109
2922
  */
3110
2923
  canDeactivateComponent(nextState) {
3111
2924
  return __awaiter(this, void 0, void 0, function* () {
3112
- // Automatically cancel any active activities if the navigation session was triggered
3113
- // by the back button.
2925
+ // Automatically cancel any active activities if the navigation session was triggered by the back button.
2926
+ // any other navigations (such as the user clicking a differnt place) must be handled by the component itself
2927
+ // during the canDeativate method. If we handled more than just the pop state then it leads to the UI ignoring
2928
+ // clicks and just cancelling things which is deeply disconcerting.
3114
2929
  if (this.navigationSession.isPopState && this.component.interactionContext && this.component.interactionContext.isActive()) {
3115
- // Note: any modal interactions run in a different router outlet so we should never get place deactivated while
3116
- // one is active. This is because:
2930
+ // Note: Modal interactions are run in a different router outlet so we never get place deactivating while
2931
+ // a model interaction is active. This is because:
3117
2932
  // 1. the user can't click anything to navigate away
3118
- // 2. clicking the back button will only change the outlet route and will leave the component route alone. This
2933
+ // 2. clicking the back button will only change the outlet route portion of the URL. This
3119
2934
  // is all handled by the InteractionGuard and so the component guards will never run.
3120
- // TODO: how will I handle this now??
3121
- // BUT: activities could call navigate while they're still active.. but we'll barf and tell them
3122
- // to call activity.done(newVisitToNavigateTo) and let the caller do the navigate after the
3123
- // dialog has closed.
3124
- // Can I capture this in placeRouter.navigate(..) ? i.e. navigationSession && navigationSession.interactionContext.isActive()
3125
- // Or can I just ignore it altogether?
3126
- // 1. I no longer have a singleton dialog interaction that can be returned from any component in the deactivation cycle.
3127
- // 2. We only ever check the component once per nav cycle
3128
- // 3. The navigation session interaction context will barf if multiple components try and use it at once.
3129
- // if (this.component.interactionContext instanceof DialogInteractionContext) {
3130
- // // BUT: activities could call navigate while they're still active.. but we'll barf and tell them
3131
- // // to call activity.done(newVisitToNavigateTo) and let the caller do the navigate after the
3132
- // // dialog has closed.
3133
- // lang.illegalState('Navigation started from an activity in a modal dialog. Have your activity return a Visit instead and navigate after the activity has finished');
3134
- // }
3135
- // Now we just cancel the current activity and stay where we are
3136
- this.cancelCurrentActivityOf(this.component.interactionContext);
3137
- return false;
2935
+ //
2936
+ // Now we just cancel the current activity...
2937
+ /** @type {?} */
2938
+ const activity = yield this.component.interactionContext.getCurrentActivity();
2939
+ activity.cancel(null);
2940
+ return false; // ..and stay where we are.
3138
2941
  }
3139
2942
  // Ok, so now we're really leaving, so we ask the component if we should.;
3140
2943
  if (this.isNotJustAChangeInRouteId(nextState) && this.component.canDeactivate) {
@@ -3146,19 +2949,6 @@ class PlaceComponentDeactivationHandler {
3146
2949
  return true;
3147
2950
  });
3148
2951
  }
3149
- /**
3150
- * @protected
3151
- * @param {?} interactionContext
3152
- * @return {?}
3153
- */
3154
- cancelCurrentActivityOf(interactionContext) {
3155
- return __awaiter(this, void 0, void 0, function* () {
3156
- /** @type {?} */
3157
- const activity = yield interactionContext.getCurrentActivity();
3158
- console.log('cancelling', { activity });
3159
- activity.cancel(null);
3160
- });
3161
- }
3162
2952
  /**
3163
2953
  * @protected
3164
2954
  * @param {?} nextState
@@ -3190,7 +2980,7 @@ if (false) {
3190
2980
  /**
3191
2981
  * @abstract
3192
2982
  */
3193
- class NavigationSession extends GarbageCollector {
2983
+ class NavigationState extends GarbageCollector {
3194
2984
  /**
3195
2985
  * @param {?} context
3196
2986
  */
@@ -3199,6 +2989,24 @@ class NavigationSession extends GarbageCollector {
3199
2989
  this.context = context;
3200
2990
  this._visits = new Map();
3201
2991
  }
2992
+ /**
2993
+ * @return {?}
2994
+ */
2995
+ get idle() {
2996
+ return !this.isTransitional;
2997
+ }
2998
+ /**
2999
+ * @return {?}
3000
+ */
3001
+ get placeRouter() {
3002
+ return this.context.placeRouter;
3003
+ }
3004
+ /**
3005
+ * @return {?}
3006
+ */
3007
+ get interactionService() {
3008
+ return this.context.interactionService;
3009
+ }
3202
3010
  /**
3203
3011
  * @return {?}
3204
3012
  */
@@ -3219,6 +3027,41 @@ class NavigationSession extends GarbageCollector {
3219
3027
  getVisitFor(placeDef) {
3220
3028
  return this._visits.get(placeDef);
3221
3029
  }
3030
+ /**
3031
+ * @param {?} event
3032
+ * @return {?}
3033
+ */
3034
+ onPopState(event) {
3035
+ return this.illegalTransition(event);
3036
+ }
3037
+ /**
3038
+ * @param {?} event
3039
+ * @return {?}
3040
+ */
3041
+ onStart(event) {
3042
+ return this.illegalTransition(event);
3043
+ }
3044
+ /**
3045
+ * @param {?} event
3046
+ * @return {?}
3047
+ */
3048
+ onCancel(event) {
3049
+ return this.illegalTransition(event);
3050
+ }
3051
+ /**
3052
+ * @param {?} event
3053
+ * @return {?}
3054
+ */
3055
+ onError(event) {
3056
+ return this.illegalTransition(event);
3057
+ }
3058
+ /**
3059
+ * @param {?} event
3060
+ * @return {?}
3061
+ */
3062
+ onEnd(event) {
3063
+ return this.illegalTransition(event);
3064
+ }
3222
3065
  /**
3223
3066
  * @param {?} newUrl
3224
3067
  * @return {?}
@@ -3226,6 +3069,16 @@ class NavigationSession extends GarbageCollector {
3226
3069
  onBackClickedDuringNavigationInteraction(newUrl) {
3227
3070
  return this.illegalTransition('onBackClickedDuringNavigationInteraction');
3228
3071
  }
3072
+ /**
3073
+ * @param {?} component
3074
+ * @param {?} nextState
3075
+ * @return {?}
3076
+ */
3077
+ canDeactivatePlace(component, nextState) {
3078
+ return __awaiter(this, void 0, void 0, function* () {
3079
+ return this.illegalTransition('canDeactivatePlace');
3080
+ });
3081
+ }
3229
3082
  /**
3230
3083
  * @return {?}
3231
3084
  */
@@ -3246,24 +3099,31 @@ class NavigationSession extends GarbageCollector {
3246
3099
  * @return {?}
3247
3100
  */
3248
3101
  currentRouterUrl() {
3249
- return this.context.router.routerState ? this.context.router.routerState.snapshot.url : null;
3102
+ return this.placeRouter.getCurrentRouterUrl();
3250
3103
  }
3251
3104
  /**
3252
3105
  * @protected
3253
3106
  * @param {?} event
3254
3107
  * @return {?}
3255
3108
  */
3256
- createActiveSession(event) {
3109
+ createTransitionStateFor(event) {
3257
3110
  // TODO: check if the event is purely for interaction context changes.
3258
- return new NavigationSession.Active(this.context, event.navigationTrigger === 'popstate', this.currentRouterUrl());
3111
+ /** @type {?} */
3112
+ const popstate = event.navigationTrigger === 'popstate';
3113
+ return popstate ?
3114
+ new NavigationState.NavigationBackTransition(this.context, popstate, this.currentRouterUrl()) :
3115
+ new NavigationState.NavigationTransition(this.context, popstate, this.currentRouterUrl());
3259
3116
  }
3260
3117
  /**
3261
- * @protected
3262
3118
  * @param {?} url
3263
3119
  * @return {?}
3264
3120
  */
3265
- updateLocation(url) {
3266
- this.context.angularLocation.go(url);
3121
+ resetBrowserLocation(url) {
3122
+ // TODO: Should this be a navigate operation to avoid confusing the router...??
3123
+ setTimeout((/**
3124
+ * @return {?}
3125
+ */
3126
+ () => this.placeRouter.resetBrowserLocation(url)));
3267
3127
  }
3268
3128
  /**
3269
3129
  * @return {?}
@@ -3272,105 +3132,55 @@ class NavigationSession extends GarbageCollector {
3272
3132
  return this.constructor.name;
3273
3133
  }
3274
3134
  }
3275
- __decorate([
3276
- Trace(),
3277
- __metadata("design:type", Function),
3278
- __metadata("design:paramtypes", [Object]),
3279
- __metadata("design:returntype", void 0)
3280
- ], NavigationSession.prototype, "updateLocation", null);
3281
3135
  if (false) {
3282
3136
  /**
3283
3137
  * @type {?}
3284
3138
  * @private
3285
3139
  */
3286
- NavigationSession.prototype._visits;
3140
+ NavigationState.prototype._visits;
3287
3141
  /** @type {?} */
3288
- NavigationSession.prototype.isPopState;
3142
+ NavigationState.prototype.isTransitional;
3289
3143
  /** @type {?} */
3290
- NavigationSession.prototype.active;
3144
+ NavigationState.prototype.startingUrl;
3291
3145
  /** @type {?} */
3292
- NavigationSession.prototype.startingUrl;
3146
+ NavigationState.prototype.isPopState;
3293
3147
  /**
3294
3148
  * @type {?}
3295
3149
  * @protected
3296
3150
  */
3297
- NavigationSession.prototype.context;
3298
- /**
3299
- * @abstract
3300
- * @param {?} event
3301
- * @return {?}
3302
- */
3303
- NavigationSession.prototype.onStart = function (event) { };
3304
- /**
3305
- * @abstract
3306
- * @param {?} event
3307
- * @return {?}
3308
- */
3309
- NavigationSession.prototype.onCancel = function (event) { };
3310
- /**
3311
- * @abstract
3312
- * @param {?} event
3313
- * @return {?}
3314
- */
3315
- NavigationSession.prototype.onError = function (event) { };
3316
- /**
3317
- * @abstract
3318
- * @param {?} event
3319
- * @return {?}
3320
- */
3321
- NavigationSession.prototype.onEnd = function (event) { };
3322
- /**
3323
- * @abstract
3324
- * @param {?} component
3325
- * @param {?} nextState
3326
- * @return {?}
3327
- */
3328
- NavigationSession.prototype.canDeactivatePlace = function (component, nextState) { };
3151
+ NavigationState.prototype.context;
3329
3152
  }
3330
- (function (NavigationSession) {
3153
+ (function (NavigationState) {
3331
3154
  class Context {
3332
3155
  /**
3333
- * @param {?} router
3334
- * @param {?} modalInteractionService
3335
- * @param {?} angularLocation
3156
+ * @param {?} placeRouter
3157
+ * @param {?} interactionService
3336
3158
  * @param {?} notifySuccess
3337
3159
  */
3338
- constructor(router, modalInteractionService, angularLocation, notifySuccess) {
3339
- this.router = router;
3340
- this.modalInteractionService = modalInteractionService;
3341
- this.angularLocation = angularLocation;
3160
+ constructor(placeRouter, interactionService, notifySuccess) {
3161
+ this.placeRouter = placeRouter;
3162
+ this.interactionService = interactionService;
3342
3163
  this.notifySuccess = notifySuccess;
3343
3164
  }
3344
3165
  }
3345
- NavigationSession.Context = Context;
3166
+ NavigationState.Context = Context;
3346
3167
  if (false) {
3347
3168
  /** @type {?} */
3348
- Context.prototype.router;
3349
- /** @type {?} */
3350
- Context.prototype.modalInteractionService;
3169
+ Context.prototype.placeRouter;
3351
3170
  /** @type {?} */
3352
- Context.prototype.angularLocation;
3171
+ Context.prototype.interactionService;
3353
3172
  /** @type {?} */
3354
3173
  Context.prototype.notifySuccess;
3355
3174
  }
3356
- class Idle extends NavigationSession {
3175
+ class Idle extends NavigationState {
3357
3176
  /**
3358
3177
  * @param {?} context
3359
3178
  */
3360
3179
  constructor(context) {
3361
3180
  super(context);
3362
- this.active = false;
3181
+ this.isTransitional = false;
3363
3182
  this.startingUrl = null;
3364
- }
3365
- /**
3366
- * @param {?} component
3367
- * @param {?} nextState
3368
- * @return {?}
3369
- */
3370
- canDeactivatePlace(component, nextState) {
3371
- return __awaiter(this, void 0, void 0, function* () {
3372
- return this.illegalTransition('canDeactivatePlace');
3373
- });
3183
+ this.isPopState = false;
3374
3184
  }
3375
3185
  /**
3376
3186
  * @param {?} event
@@ -3382,44 +3192,35 @@ if (false) {
3382
3192
  Logger.get(this).info(`navigation started to same url -> ${event.url}`);
3383
3193
  return this;
3384
3194
  }
3385
- if (event.url === (`${this.currentRouterUrl()}(aup-interaction:modal)`)) {
3195
+ if (this.placeRouter.hasActiveInteractionIds(event.url)) {
3386
3196
  Logger.get(this).info(`navigation started with interaction outlet -> ${event.url}`);
3387
- return new ModalInteractionSession(this.context, event.url);
3197
+ return new InteractionTransition(this.context, event.url);
3198
+ }
3199
+ else {
3200
+ return this.createTransitionStateFor(event);
3388
3201
  }
3389
- return this.createActiveSession(event);
3390
- }
3391
- /**
3392
- * @param {?} event
3393
- * @return {?}
3394
- */
3395
- onCancel(event) {
3396
- return this.illegalTransition(event);
3397
- }
3398
- /**
3399
- * @param {?} event
3400
- * @return {?}
3401
- */
3402
- onEnd(event) {
3403
- return this.illegalTransition(event);
3404
3202
  }
3405
3203
  /**
3406
3204
  * @param {?} event
3407
3205
  * @return {?}
3408
3206
  */
3409
- onError(event) {
3410
- return this.illegalTransition(event);
3207
+ onPopState(event) {
3208
+ return this.createTransitionStateFor(event);
3411
3209
  }
3412
3210
  }
3413
- NavigationSession.Idle = Idle;
3211
+ NavigationState.Idle = Idle;
3414
3212
  if (false) {
3415
3213
  /** @type {?} */
3416
- Idle.prototype.isPopState;
3417
- /** @type {?} */
3418
- Idle.prototype.active;
3214
+ Idle.prototype.isTransitional;
3419
3215
  /** @type {?} */
3420
3216
  Idle.prototype.startingUrl;
3217
+ /** @type {?} */
3218
+ Idle.prototype.isPopState;
3421
3219
  }
3422
- class Active extends NavigationSession {
3220
+ /**
3221
+ * @abstract
3222
+ */
3223
+ class AbstractNavigationTransition extends NavigationState {
3423
3224
  /**
3424
3225
  * @param {?} context
3425
3226
  * @param {?} isPopState
@@ -3429,9 +3230,9 @@ if (false) {
3429
3230
  super(context);
3430
3231
  this.isPopState = isPopState;
3431
3232
  this.startingUrl = startingUrl;
3432
- this.active = true;
3233
+ this.isTransitional = true;
3433
3234
  this.componentDeactivationHandlers = new Map();
3434
- this._interactionContext = this.context.modalInteractionService.createExclusiveInteractionContext();
3235
+ this._interactionContext = this.interactionService._createExclusiveModalInteractionContext();
3435
3236
  this.onDispose((/**
3436
3237
  * @return {?}
3437
3238
  */
@@ -3439,9 +3240,9 @@ if (false) {
3439
3240
  // the interaction context can be detached during the back button cancellation state transition
3440
3241
  // as the transition is synchronous and activityCancellation isn't. Otherwise dispose will be
3441
3242
  // called before the context has been cancelled. It might be work having the interaction context
3442
- // automatically cancel if the context is disposed.
3243
+ // automatically cancel if the context is disposed so we don't have worry about detaching etc.
3443
3244
  if (this._interactionContext) {
3444
- this._interactionContext.dispose();
3245
+ this._interactionContext.dispose(); // or do something like cancelAndDispose?
3445
3246
  }
3446
3247
  }));
3447
3248
  }
@@ -3456,7 +3257,8 @@ if (false) {
3456
3257
  * @return {?}
3457
3258
  */
3458
3259
  onStart(event) {
3459
- // active sessions can have many cancel start cycles.
3260
+ // active sessions can have many cancel start cycles due
3261
+ // to place guard redirects
3460
3262
  return this;
3461
3263
  }
3462
3264
  /**
@@ -3468,53 +3270,27 @@ if (false) {
3468
3270
  this.context.notifySuccess(this);
3469
3271
  return new Idle(this.context);
3470
3272
  }
3471
- /**
3472
- * @param {?} event
3473
- * @return {?}
3474
- */
3475
- onCancel(event) {
3476
- // active sessions can have many cancel start cycles.
3477
- return this;
3478
- }
3479
- /**
3480
- * @param {?} event
3481
- * @return {?}
3482
- */
3483
- onError(event) {
3484
- // navigation was aborted.
3485
- if (this.isPopState && this.currentRouterUrl() !== this.startingUrl) {
3486
- // Angular doesn't preserve the url when a guard cancels the back button.
3487
- // See https://github.com/angular/angular/issues/13586#issuecomment-432795720
3488
- Logger.get(this).info('WORK-AROUND: Updating browser location after pop state - see angular issue #13586');
3489
- this.updateLocation(this.startingUrl);
3490
- }
3491
- return new Idle(this.context);
3492
- }
3493
3273
  /**
3494
3274
  * @param {?} locationTriggerUrl
3495
3275
  * @return {?}
3496
3276
  */
3497
3277
  onBackClickedDuringNavigationInteraction(locationTriggerUrl) {
3278
+ // detach the interactoin from the session so it doesn't get disposed until the activity
3279
+ // has completed.
3498
3280
  /** @type {?} */
3499
3281
  const context = this.detachInteractionContext();
3282
+ const { when } = Dsl.disposeWith(context);
3283
+ // TODO: I need to make the exclusive interaction context disallow nested activities or
3284
+ // that would mess things up entirely.
3500
3285
  context.getCurrentActivity().then((/**
3501
3286
  * @param {?} activity
3502
3287
  * @return {?}
3503
3288
  */
3504
3289
  activity => {
3505
- context.addActivityListener({
3506
- /**
3507
- * @return {?}
3508
- */
3509
- onActivityFinished() {
3510
- context.dispose();
3511
- },
3512
- /**
3513
- * @return {?}
3514
- */
3515
- onActivityStarted() {
3516
- }
3517
- });
3290
+ when.valueOf(context.active).becomesFalsey((/**
3291
+ * @return {?}
3292
+ */
3293
+ () => context.dispose()), { once: true });
3518
3294
  activity.cancel(null);
3519
3295
  }));
3520
3296
  return new CancelledDuringNavigationInteraction(this.context, this.startingUrl, locationTriggerUrl);
@@ -3548,33 +3324,116 @@ if (false) {
3548
3324
  this._interactionContext = null;
3549
3325
  return context;
3550
3326
  }
3551
- /**
3552
- * @return {?}
3553
- */
3554
- toString() {
3555
- return `${this.constructor.name}(startingUrl: ${this.startingUrl}, isPopState:${this.isPopState})`;
3556
- }
3557
3327
  }
3558
- NavigationSession.Active = Active;
3328
+ NavigationState.AbstractNavigationTransition = AbstractNavigationTransition;
3559
3329
  if (false) {
3560
3330
  /** @type {?} */
3561
- Active.prototype.active;
3331
+ AbstractNavigationTransition.prototype.isTransitional;
3562
3332
  /**
3563
3333
  * @type {?}
3564
3334
  * @private
3565
3335
  */
3566
- Active.prototype.componentDeactivationHandlers;
3336
+ AbstractNavigationTransition.prototype.componentDeactivationHandlers;
3567
3337
  /**
3568
3338
  * @type {?}
3569
3339
  * @private
3570
3340
  */
3571
- Active.prototype._interactionContext;
3341
+ AbstractNavigationTransition.prototype._interactionContext;
3342
+ /** @type {?} */
3343
+ AbstractNavigationTransition.prototype.isPopState;
3344
+ /** @type {?} */
3345
+ AbstractNavigationTransition.prototype.startingUrl;
3346
+ }
3347
+ class NavigationTransition extends AbstractNavigationTransition {
3348
+ constructor() {
3349
+ super(...arguments);
3350
+ this.isPopState = false;
3351
+ }
3352
+ /**
3353
+ * @param {?} event
3354
+ * @return {?}
3355
+ */
3356
+ onStart(event) {
3357
+ // active sessions can have many cancel start cycles due
3358
+ // to place guard redirects
3359
+ return this;
3360
+ }
3361
+ /**
3362
+ * @param {?} event
3363
+ * @return {?}
3364
+ */
3365
+ onEnd(event) {
3366
+ // navigation succeeded
3367
+ this.context.notifySuccess(this);
3368
+ return new Idle(this.context);
3369
+ }
3370
+ /**
3371
+ * @param {?} event
3372
+ * @return {?}
3373
+ */
3374
+ onCancel(event) {
3375
+ return new Idle(this.context);
3376
+ }
3377
+ /**
3378
+ * @param {?} event
3379
+ * @return {?}
3380
+ */
3381
+ onError(event) {
3382
+ // navigation was aborted.
3383
+ return new Idle(this.context);
3384
+ }
3385
+ /**
3386
+ * @return {?}
3387
+ */
3388
+ toString() {
3389
+ return `${this.constructor.name}(startingUrl: ${this.startingUrl})`;
3390
+ }
3391
+ }
3392
+ NavigationState.NavigationTransition = NavigationTransition;
3393
+ if (false) {
3572
3394
  /** @type {?} */
3573
- Active.prototype.isPopState;
3395
+ NavigationTransition.prototype.isPopState;
3396
+ }
3397
+ class NavigationBackTransition extends AbstractNavigationTransition {
3398
+ constructor() {
3399
+ super(...arguments);
3400
+ this.isPopState = true;
3401
+ }
3402
+ /**
3403
+ * @param {?} event
3404
+ * @return {?}
3405
+ */
3406
+ onCancel(event) {
3407
+ // Angular doesn't preserve the url when a guard cancels the back button.
3408
+ // See https://github.com/angular/angular/issues/13586#issuecomment-432795720
3409
+ Logger.get(this).info('WORK-AROUND: Updating browser location after pop state - see angular issue #13586');
3410
+ this.resetBrowserLocation(this.startingUrl);
3411
+ return new Idle(this.context);
3412
+ }
3413
+ /**
3414
+ * @param {?} event
3415
+ * @return {?}
3416
+ */
3417
+ onError(event) {
3418
+ // navigation was aborted.
3419
+ if (this.currentRouterUrl() !== this.startingUrl) {
3420
+ // Angular doesn't preserve the url when a guard cancels the back button.
3421
+ // See https://github.com/angular/angular/issues/13586#issuecomment-432795720
3422
+ Logger.get(this).info('WORK-AROUND: Updating browser location after pop state - see angular issue #13586');
3423
+ this.resetBrowserLocation(this.startingUrl);
3424
+ }
3425
+ return new Idle(this.context);
3426
+ }
3427
+ }
3428
+ NavigationState.NavigationBackTransition = NavigationBackTransition;
3429
+ if (false) {
3574
3430
  /** @type {?} */
3575
- Active.prototype.startingUrl;
3431
+ NavigationBackTransition.prototype.isPopState;
3576
3432
  }
3577
- class ModalInteractionSession extends NavigationSession {
3433
+ /**
3434
+ * @abstract
3435
+ */
3436
+ class AbstractInteractionTransition extends NavigationState {
3578
3437
  /**
3579
3438
  * @param {?} context
3580
3439
  * @param {?} startingUrl
@@ -3582,100 +3441,119 @@ if (false) {
3582
3441
  constructor(context, startingUrl) {
3583
3442
  super(context);
3584
3443
  this.startingUrl = startingUrl;
3585
- this.active = false;
3586
- this.isPopState = false;
3444
+ this.isTransitional = true;
3587
3445
  }
3588
3446
  /**
3589
- * @param {?} url
3447
+ * @protected
3590
3448
  * @return {?}
3591
3449
  */
3592
- static hasInteraction(url) {
3593
- return url.endsWith('(aup-interaction:modal)');
3450
+ reinstateInteractionRoute() {
3451
+ console.log(this.startingUrl);
3452
+ setTimeout((/**
3453
+ * @return {?}
3454
+ */
3455
+ () => this.placeRouter.syncInteractionIdsWithRouter()));
3456
+ }
3457
+ }
3458
+ NavigationState.AbstractInteractionTransition = AbstractInteractionTransition;
3459
+ if (false) {
3460
+ /** @type {?} */
3461
+ AbstractInteractionTransition.prototype.isTransitional;
3462
+ /** @type {?} */
3463
+ AbstractInteractionTransition.prototype.startingUrl;
3464
+ }
3465
+ /**
3466
+ * This state exists to handle all events while any kind of navigation is in progress. That way all other states can
3467
+ * happily ignore interaction contexts.
3468
+ */
3469
+ class InteractionTransition extends AbstractInteractionTransition {
3470
+ constructor() {
3471
+ super(...arguments);
3472
+ this.isPopState = false;
3594
3473
  }
3595
3474
  /**
3596
3475
  * @param {?} event
3597
3476
  * @return {?}
3598
3477
  */
3599
- onStart(event) {
3600
- // VERY VERY IMPORTANT BACK BUTTON NOTE:
3601
- // When the back button is clicked we'll enter here first, and push the url
3602
- // back to the browser. Angular seems to ignore it from a routing perspective
3603
- // and then the InteractionGuard will cancel the navigation. This process seems
3604
- // to keep the brower history in a sane state.
3605
- if (this.context.modalInteractionService.isActive()) {
3606
- if (!ModalInteractionSession.hasInteraction(event.url)) {
3607
- // this capture the case where
3608
- this.updateLocation(this.startingUrl);
3609
- }
3478
+ onEnd(event) {
3479
+ if (this.context.interactionService.isActive()) {
3480
+ this.reinstateInteractionRoute();
3481
+ return new IdleDuringInteraction(this.context, this.startingUrl);
3482
+ }
3483
+ else {
3484
+ return new Idle(this.context);
3610
3485
  }
3611
- return this;
3612
3486
  }
3613
- /**
3614
- * @param {?} event
3615
- * @return {?}
3616
- */
3617
- onCancel(event) {
3618
- // this.updateLocation(this.startingUrl);
3619
- return this;
3487
+ }
3488
+ NavigationState.InteractionTransition = InteractionTransition;
3489
+ if (false) {
3490
+ /** @type {?} */
3491
+ InteractionTransition.prototype.isPopState;
3492
+ }
3493
+ /**
3494
+ * This state exists to handle all events while any kind of navigation is in progress. That way all other states can
3495
+ * happily ignore interaction contexts.
3496
+ */
3497
+ class InteractionBackTransition extends AbstractInteractionTransition {
3498
+ constructor() {
3499
+ super(...arguments);
3500
+ this.isPopState = true;
3620
3501
  }
3621
3502
  /**
3622
3503
  * @param {?} event
3623
3504
  * @return {?}
3624
3505
  */
3625
3506
  onEnd(event) {
3626
- if (this.context.modalInteractionService.isActive()) {
3627
- return this;
3507
+ if (this.interactionService.isActive()) {
3508
+ this.reinstateInteractionRoute();
3509
+ return new IdleDuringInteraction(this.context, this.startingUrl);
3628
3510
  }
3629
3511
  else {
3630
3512
  return new Idle(this.context);
3631
3513
  }
3632
3514
  }
3515
+ }
3516
+ NavigationState.InteractionBackTransition = InteractionBackTransition;
3517
+ if (false) {
3518
+ /** @type {?} */
3519
+ InteractionBackTransition.prototype.isPopState;
3520
+ }
3521
+ class IdleDuringInteraction extends NavigationState {
3522
+ /**
3523
+ * @param {?} context
3524
+ * @param {?} startingUrl
3525
+ */
3526
+ constructor(context, startingUrl) {
3527
+ super(context);
3528
+ this.startingUrl = startingUrl;
3529
+ this.isTransitional = false;
3530
+ this.isPopState = false;
3531
+ }
3633
3532
  /**
3634
3533
  * @param {?} event
3635
3534
  * @return {?}
3636
3535
  */
3637
- onError(event) {
3638
- return this.illegalTransition(event);
3536
+ onStart(event) {
3537
+ return new InteractionTransition(this.context, event.url);
3639
3538
  }
3640
3539
  /**
3641
- * @param {?} component
3642
- * @param {?} nextState
3540
+ * @param {?} event
3643
3541
  * @return {?}
3644
3542
  */
3645
- canDeactivatePlace(component, nextState) {
3646
- return __awaiter(this, void 0, void 0, function* () {
3647
- return true;
3648
- });
3543
+ onPopState(event) {
3544
+ return new InteractionBackTransition(this.context, event.url);
3649
3545
  }
3650
3546
  }
3651
- __decorate([
3652
- Trace(),
3653
- __metadata("design:type", Function),
3654
- __metadata("design:paramtypes", [NavigationStart]),
3655
- __metadata("design:returntype", NavigationSession)
3656
- ], ModalInteractionSession.prototype, "onStart", null);
3657
- __decorate([
3658
- Trace(),
3659
- __metadata("design:type", Function),
3660
- __metadata("design:paramtypes", [NavigationCancel]),
3661
- __metadata("design:returntype", NavigationSession)
3662
- ], ModalInteractionSession.prototype, "onCancel", null);
3663
- __decorate([
3664
- Trace(),
3665
- __metadata("design:type", Function),
3666
- __metadata("design:paramtypes", [NavigationEnd]),
3667
- __metadata("design:returntype", NavigationSession)
3668
- ], ModalInteractionSession.prototype, "onEnd", null);
3669
- NavigationSession.ModalInteractionSession = ModalInteractionSession;
3547
+ NavigationState.IdleDuringInteraction = IdleDuringInteraction;
3670
3548
  if (false) {
3671
3549
  /** @type {?} */
3672
- ModalInteractionSession.prototype.active;
3550
+ IdleDuringInteraction.prototype.isTransitional;
3673
3551
  /** @type {?} */
3674
- ModalInteractionSession.prototype.isPopState;
3552
+ IdleDuringInteraction.prototype.isPopState;
3675
3553
  /** @type {?} */
3676
- ModalInteractionSession.prototype.startingUrl;
3554
+ IdleDuringInteraction.prototype.startingUrl;
3677
3555
  }
3678
- class CancelledDuringNavigationInteraction extends NavigationSession {
3556
+ class CancelledDuringNavigationInteraction extends NavigationState {
3679
3557
  /**
3680
3558
  * @param {?} context
3681
3559
  * @param {?} startingUrl
@@ -3685,20 +3563,27 @@ if (false) {
3685
3563
  super(context);
3686
3564
  this.startingUrl = startingUrl;
3687
3565
  this.locationChangeTriggerUrl = locationChangeTriggerUrl;
3688
- this.active = false;
3566
+ this.isPopState = false;
3689
3567
  this.capturedFauxRouterStart = false;
3690
- // This will trigger a return to the route we originally started with.
3691
- // this.angularLocation.go(this.startingUrl);
3692
3568
  }
3693
3569
  /**
3694
- * @param {?} component
3695
- * @param {?} nextState
3696
3570
  * @return {?}
3697
3571
  */
3698
- canDeactivatePlace(component, nextState) {
3699
- return __awaiter(this, void 0, void 0, function* () {
3700
- return false;
3701
- });
3572
+ get isTransitional() {
3573
+ return !this.capturedFauxRouterStart;
3574
+ }
3575
+ /**
3576
+ * @param {?} event
3577
+ * @return {?}
3578
+ */
3579
+ onStart(event) {
3580
+ if (event.url === this.locationChangeTriggerUrl && !this.capturedFauxRouterStart) {
3581
+ this.capturedFauxRouterStart = true;
3582
+ return this.ignore(event, 'url matched back button location change');
3583
+ }
3584
+ else {
3585
+ return this.createTransitionStateFor(event);
3586
+ }
3702
3587
  }
3703
3588
  /**
3704
3589
  * @param {?} event
@@ -3725,14 +3610,8 @@ if (false) {
3725
3610
  * @param {?} event
3726
3611
  * @return {?}
3727
3612
  */
3728
- onStart(event) {
3729
- if (event.url === this.locationChangeTriggerUrl && !this.capturedFauxRouterStart) {
3730
- this.capturedFauxRouterStart = true;
3731
- return this.ignore(event, 'url matched back button location change');
3732
- }
3733
- else {
3734
- return this.createActiveSession(event);
3735
- }
3613
+ onPopState(event) {
3614
+ return this.createTransitionStateFor(event);
3736
3615
  }
3737
3616
  /**
3738
3617
  * @param {?} event
@@ -3751,10 +3630,8 @@ if (false) {
3751
3630
  return `${this.constructor.name}(startingUrl: ${this.startingUrl}, locationChangeTriggerUrl:${this.locationChangeTriggerUrl})`;
3752
3631
  }
3753
3632
  }
3754
- NavigationSession.CancelledDuringNavigationInteraction = CancelledDuringNavigationInteraction;
3633
+ NavigationState.CancelledDuringNavigationInteraction = CancelledDuringNavigationInteraction;
3755
3634
  if (false) {
3756
- /** @type {?} */
3757
- CancelledDuringNavigationInteraction.prototype.active;
3758
3635
  /** @type {?} */
3759
3636
  CancelledDuringNavigationInteraction.prototype.isPopState;
3760
3637
  /**
@@ -3767,7 +3644,7 @@ if (false) {
3767
3644
  /** @type {?} */
3768
3645
  CancelledDuringNavigationInteraction.prototype.locationChangeTriggerUrl;
3769
3646
  }
3770
- })(NavigationSession || (NavigationSession = {}));
3647
+ })(NavigationState || (NavigationState = {}));
3771
3648
 
3772
3649
  /**
3773
3650
  * @fileoverview added by tsickle
@@ -3836,29 +3713,27 @@ if (false) {
3836
3713
  * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
3837
3714
  */
3838
3715
  class UrlSnapshot {
3716
+ // TODO: Update this accept a url Parser so it can be immutable and generate new trees on mutation using toString() are parseUrl.
3839
3717
  /**
3840
- * @param {?} urlTree
3841
- */
3842
- constructor(urlTree) {
3843
- this.urlTree = urlTree;
3844
- // console.log({ segments: this.urlTree.root.children.primary.segments });
3845
- }
3846
- /**
3847
- * @return {?}
3718
+ * @param {?} urlSerializer
3719
+ * @param {?} url
3848
3720
  */
3849
- cloneUrlSegmentList() {
3850
- return [...this.urlTree.root.children.primary.segments];
3721
+ constructor(urlSerializer, url) {
3722
+ this.urlSerializer = urlSerializer;
3723
+ this.url = url;
3724
+ this.urlTree = urlSerializer.parse(url);
3851
3725
  }
3852
3726
  /**
3727
+ * @protected
3853
3728
  * @param {?} visit
3854
3729
  * @return {?}
3855
3730
  */
3856
- updateVisitSegments(visit) {
3731
+ replaceExistingVisitSegmentsWith(visit) {
3857
3732
  // Ugly, but it works for now.
3858
3733
  /** @type {?} */
3859
- const segments = this.cloneUrlSegmentList();
3734
+ const segments = [...this.getPrimarySegments()];
3860
3735
  /** @type {?} */
3861
- const visitSegments = this.convertToUrlSegments(visit);
3736
+ const visitSegments = this.getSegmentsFor(visit);
3862
3737
  /** @type {?} */
3863
3738
  const replaceAt = segments.findIndex((/**
3864
3739
  * @param {?} segment
@@ -3869,12 +3744,20 @@ class UrlSnapshot {
3869
3744
  segments.splice(replaceAt, visitSegments.length, ...visitSegments);
3870
3745
  return segments;
3871
3746
  }
3747
+ /**
3748
+ * @private
3749
+ * @return {?}
3750
+ */
3751
+ getPrimarySegments() {
3752
+ return this.urlTree.root.children.primary.segments;
3753
+ }
3872
3754
  /**
3873
3755
  * Converts the visit into segments. Please not that these segments are not e
3756
+ * @protected
3874
3757
  * @param {?} visit
3875
3758
  * @return {?}
3876
3759
  */
3877
- convertToUrlSegments(visit) {
3760
+ getSegmentsFor(visit) {
3878
3761
  return visit.placeDefinition.hasRouteId() ?
3879
3762
  [
3880
3763
  // NOTE:
@@ -3894,7 +3777,7 @@ class UrlSnapshot {
3894
3777
  */
3895
3778
  createRedirectCommandsFor(visit) {
3896
3779
  /** @type {?} */
3897
- const segments = this.updateVisitSegments(visit);
3780
+ const segments = this.replaceExistingVisitSegmentsWith(visit);
3898
3781
  /** @type {?} */
3899
3782
  const commands = [];
3900
3783
  segments.forEach((/**
@@ -3914,17 +3797,82 @@ class UrlSnapshot {
3914
3797
  * @return {?}
3915
3798
  */
3916
3799
  includesPathOf(placeDef) {
3917
- return this.cloneUrlSegmentList().find((/**
3800
+ return this.getPrimarySegments().find((/**
3918
3801
  * @param {?} s
3919
3802
  * @return {?}
3920
3803
  */
3921
3804
  s => s.path === placeDef.path));
3922
3805
  }
3806
+ /**
3807
+ * @return {?}
3808
+ */
3809
+ getInteractionIds() {
3810
+ /** @type {?} */
3811
+ const interactionOutlet = this.urlTree.root.children[UrlSnapshot.INTERACTION_ROUTER_OUTLET];
3812
+ if (interactionOutlet) {
3813
+ assert.isTruthy(interactionOutlet.segments.length === 2);
3814
+ assert.isTruthy(interactionOutlet.segments[0].path === UrlSnapshot.INTERACTION_ROUTER_PATH);
3815
+ return UrlSnapshot.parseInteractionIds(interactionOutlet.segments[1].path);
3816
+ }
3817
+ else {
3818
+ return [];
3819
+ }
3820
+ }
3821
+ // @Trace()
3822
+ /**
3823
+ * @param {?} ids
3824
+ * @return {?}
3825
+ */
3826
+ addOrReplaceInteractionIds(ids) {
3827
+ /** @type {?} */
3828
+ const urlTree = this.urlSerializer.parse(this.url);
3829
+ urlTree.root.children[UrlSnapshot.INTERACTION_ROUTER_OUTLET] = new UrlSegmentGroup([
3830
+ new UrlSegment(UrlSnapshot.INTERACTION_ROUTER_PATH, {}),
3831
+ new UrlSegment(UrlSnapshot.createPathIdFor(ids), {})
3832
+ ], {});
3833
+ return new UrlSnapshot(this.urlSerializer, urlTree.toString());
3834
+ }
3923
3835
  }
3924
3836
  if (false) {
3925
- /** @type {?} */
3837
+ /**
3838
+ * @type {?}
3839
+ * @private
3840
+ */
3926
3841
  UrlSnapshot.prototype.urlTree;
3842
+ /** @type {?} */
3843
+ UrlSnapshot.prototype.urlSerializer;
3844
+ /** @type {?} */
3845
+ UrlSnapshot.prototype.url;
3927
3846
  }
3847
+ (function (UrlSnapshot) {
3848
+ UrlSnapshot.INTERACTION_ROUTER_OUTLET = 'aup-interactions';
3849
+ UrlSnapshot.INTERACTION_ROUTER_PATH = 'active';
3850
+ UrlSnapshot.INTERACTION_ID_SEPARATOR = '--';
3851
+ /**
3852
+ * @param {?} path
3853
+ * @return {?}
3854
+ */
3855
+ function parseInteractionIds(path) {
3856
+ return path.split(UrlSnapshot.INTERACTION_ID_SEPARATOR);
3857
+ }
3858
+ UrlSnapshot.parseInteractionIds = parseInteractionIds;
3859
+ /**
3860
+ * @param {?} interactionIds
3861
+ * @return {?}
3862
+ */
3863
+ function createPathIdFor(interactionIds) {
3864
+ return interactionIds.join(UrlSnapshot.INTERACTION_ID_SEPARATOR);
3865
+ }
3866
+ UrlSnapshot.createPathIdFor = createPathIdFor;
3867
+ /**
3868
+ * @param {?} interactionIds
3869
+ * @return {?}
3870
+ */
3871
+ function createInteractionOutletRouterCommands(interactionIds) {
3872
+ return [UrlSnapshot.INTERACTION_ROUTER_PATH, createPathIdFor(interactionIds)];
3873
+ }
3874
+ UrlSnapshot.createInteractionOutletRouterCommands = createInteractionOutletRouterCommands;
3875
+ })(UrlSnapshot || (UrlSnapshot = {}));
3928
3876
 
3929
3877
  /**
3930
3878
  * @fileoverview added by tsickle
@@ -3936,29 +3884,33 @@ class PlaceRouter extends GarbageCollector {
3936
3884
  * @param {?} urlSerializer
3937
3885
  * @param {?} angularLocation
3938
3886
  * @param {?} placeHistory
3939
- * @param {?} modalInteractionService
3887
+ * @param {?} interactionService
3940
3888
  */
3941
- constructor(router, urlSerializer, angularLocation, placeHistory, modalInteractionService) {
3889
+ constructor(router, urlSerializer, angularLocation, placeHistory, interactionService) {
3942
3890
  super();
3943
3891
  this.router = router;
3944
3892
  this.urlSerializer = urlSerializer;
3945
3893
  this.angularLocation = angularLocation;
3946
3894
  this.placeHistory = placeHistory;
3947
- this.modalInteractionService = modalInteractionService;
3948
- this.firstRoute = true;
3949
- this._navigationSessionModel = new MutableValueModel();
3895
+ this.interactionService = interactionService;
3896
+ this._navigationStateModel = new MutableValueModel();
3950
3897
  this._activeVisits = new MutableListModel();
3951
3898
  const { chain, valueOf, before, when, after, observe, switchOn } = Dsl.disposeWith(this);
3952
3899
  this.activeVisitIndex = chain(this._activeVisits).indexBy('placeDefinition');
3953
- this.navigationSessionActive = chain(this.navigationSessionModel).pluck('active');
3954
- this._navigationSessionContext = new NavigationSession.Context(this.router, this.modalInteractionService, this.angularLocation, (/**
3900
+ this.navigationInProgress = chain(this.navigationStateModel).pluck('isTransitional');
3901
+ this._navigationSessionContext = new NavigationState.Context(this, this.interactionService, (/**
3955
3902
  * @param {?} session
3956
3903
  * @return {?}
3957
3904
  */
3958
3905
  session => {
3959
3906
  this.processNavigationSuccess(session);
3960
3907
  }));
3961
- this._navigationSessionModel.value = new NavigationSession.Idle(this._navigationSessionContext);
3908
+ this._navigationStateModel.value = new NavigationState.Idle(this._navigationSessionContext);
3909
+ this._navigationStateTypeModel = chain(this._navigationStateModel).map((/**
3910
+ * @param {?} state
3911
+ * @return {?}
3912
+ */
3913
+ state => (/** @type {?} */ (state.constructor))));
3962
3914
  // TODO: make setup the callbacks in during module initiation to make this testable.
3963
3915
  this.router.events.subscribe((/**
3964
3916
  * @param {?} event
@@ -3972,53 +3924,85 @@ class PlaceRouter extends GarbageCollector {
3972
3924
  // NavigationStart -> .... -> NavigationError --> navigation aborted, end session.
3973
3925
  // =======================
3974
3926
  if (event instanceof NavigationStart) {
3975
- this.runStateTransition((/**
3976
- * @param {?} session
3977
- * @return {?}
3978
- */
3979
- session => session.onStart(event)));
3927
+ console.log(event);
3928
+ if (event.navigationTrigger === 'popstate') {
3929
+ this.runStateTransition((/**
3930
+ * @param {?} state
3931
+ * @return {?}
3932
+ */
3933
+ state => state.onPopState(event)));
3934
+ }
3935
+ else {
3936
+ this.runStateTransition((/**
3937
+ * @param {?} state
3938
+ * @return {?}
3939
+ */
3940
+ state => state.onStart(event)));
3941
+ }
3980
3942
  }
3981
3943
  if (event instanceof NavigationEnd) {
3944
+ console.log(event);
3982
3945
  this.runStateTransition((/**
3983
- * @param {?} session
3946
+ * @param {?} state
3984
3947
  * @return {?}
3985
3948
  */
3986
- session => session.onEnd(event)));
3949
+ state => state.onEnd(event)));
3987
3950
  }
3988
3951
  if (event instanceof NavigationError) {
3952
+ console.log(event);
3989
3953
  this.runStateTransition((/**
3990
- * @param {?} session
3954
+ * @param {?} state
3991
3955
  * @return {?}
3992
3956
  */
3993
- session => session.onError(event)));
3957
+ state => state.onError(event)));
3994
3958
  }
3995
3959
  if (event instanceof NavigationCancel) {
3960
+ console.log(event);
3996
3961
  this.runStateTransition((/**
3997
- * @param {?} session
3962
+ * @param {?} state
3998
3963
  * @return {?}
3999
3964
  */
4000
- session => session.onCancel(event)));
3965
+ state => state.onCancel(event)));
4001
3966
  }
4002
3967
  }));
4003
3968
  // Push dialog state to the url so we can capture the back button.
4004
- this.modalInteractionService.addActivityListener(new PlaceRouter.InteractionRouteMediator(this.navigationSessionActive, this.router));
3969
+ when.listOf(this.interactionService.activeInteractionContextIds).changes((/**
3970
+ * @param {?} ids
3971
+ * @param {?} previous
3972
+ * @return {?}
3973
+ */
3974
+ (ids, previous) => {
3975
+ this.syncInteractionIdsWithRouter();
3976
+ }), { unless: this.navigationInProgress }); // TODO: I think the exclusive interaction prevents interactions starting while it's active so we might not need this.
3977
+ // TODO: I think the exclusive interaction prevents interactions starting while it's active so we might not need this.
3978
+ /** @type {?} */
3979
+ const urlChanges = new MutableStream();
4005
3980
  // The angular router doesn't always fire router events when the back button is pushed while a navigation
4006
3981
  // session is in progress. Sometimes we only know about it from the url change.
3982
+ // IMPORTANT ORDER DEPENDENCY
3983
+ // This only works because we're notified of the change after the router has started reacting to it. This
3984
+ // we can can use our navigationState to determine things.
4007
3985
  angularLocation.onUrlChange((/**
4008
3986
  * @param {?} url
4009
3987
  * @return {?}
4010
3988
  */
4011
3989
  url => {
4012
- console.log(`#### url changed -> ${url}`);
4013
3990
  /** @type {?} */
4014
- const interactionContext = this.navigationSessionActive.value && this.navigationSession.interactionContext;
4015
- if (interactionContext && interactionContext.isActive()) {
4016
- Logger.get(this).info(`back button pressed during navigation session interaction`);
4017
- this.runStateTransition((/**
4018
- * @param {?} navigationSession
4019
- * @return {?}
4020
- */
4021
- navigationSession => navigationSession.onBackClickedDuringNavigationInteraction(url)));
3991
+ const navigationState = this._navigationStateModel.value;
3992
+ console.log(`URLChange -> ${url}`, { state: navigationState });
3993
+ urlChanges.publish({ url, state: navigationState });
3994
+ // We've entered a navigation transition
3995
+ if (navigationState instanceof NavigationState.NavigationTransition) {
3996
+ /** @type {?} */
3997
+ const navigationInteraction = this.navigationState.interactionContext;
3998
+ if (navigationInteraction && navigationInteraction.isActive()) {
3999
+ Logger.get(this).info(`back button pressed during navigation session interaction promise`);
4000
+ this.runStateTransition((/**
4001
+ * @param {?} state
4002
+ * @return {?}
4003
+ */
4004
+ state => state.onBackClickedDuringNavigationInteraction(url)));
4005
+ }
4022
4006
  }
4023
4007
  }));
4024
4008
  }
@@ -4028,6 +4012,9 @@ class PlaceRouter extends GarbageCollector {
4028
4012
  * @return {?}
4029
4013
  */
4030
4014
  processNavigationSuccess(session) {
4015
+ // We need to update the visits before the session finishes. This allows the placeOutets to ignore visit
4016
+ // changes that occur while routerNavigationActive is true.
4017
+ assert.isTruthy(this.navigationInProgress.value);
4031
4018
  /** @type {?} */
4032
4019
  const visits = session.getVisits();
4033
4020
  visits.forEach((/**
@@ -4035,21 +4022,19 @@ class PlaceRouter extends GarbageCollector {
4035
4022
  * @return {?}
4036
4023
  */
4037
4024
  v => this.placeHistory.add(v)));
4038
- // Update visits before we end the navigation session. This allows the placeOutets to
4039
- // ignore visit changes that occur while the navigation is in progress
4040
4025
  this._activeVisits.value = visits;
4041
4026
  }
4042
4027
  /**
4043
4028
  * @return {?}
4044
4029
  */
4045
- get navigationSession() {
4046
- return this._navigationSessionModel.value;
4030
+ get navigationState() {
4031
+ return this._navigationStateModel.value;
4047
4032
  }
4048
4033
  /**
4049
4034
  * @return {?}
4050
4035
  */
4051
- get navigationSessionModel() {
4052
- return this._navigationSessionModel.readonly;
4036
+ get navigationStateModel() {
4037
+ return this._navigationStateModel.readonly;
4053
4038
  }
4054
4039
  /**
4055
4040
  * @return {?}
@@ -4101,7 +4086,7 @@ class PlaceRouter extends GarbageCollector {
4101
4086
  */
4102
4087
  router => {
4103
4088
  /** @type {?} */
4104
- const commands = this.parseUrl(this.router.routerState.snapshot).createRedirectCommandsFor(next);
4089
+ const commands = this.parseUrl(this.router.routerState.snapshot.url).createRedirectCommandsFor(next);
4105
4090
  console.log('### Push Changes to route Redirect', { commands });
4106
4091
  return router.navigate(commands);
4107
4092
  }));
@@ -4115,7 +4100,7 @@ class PlaceRouter extends GarbageCollector {
4115
4100
  */
4116
4101
  doNavigation(visit, runNavigationCommands) {
4117
4102
  return __awaiter(this, void 0, void 0, function* () {
4118
- if (this.navigationSessionActive.value) {
4103
+ if (this.navigationInProgress.value) {
4119
4104
  lang.illegalState('Navigation already in progress');
4120
4105
  }
4121
4106
  this.runStateTransition((/**
@@ -4124,7 +4109,7 @@ class PlaceRouter extends GarbageCollector {
4124
4109
  */
4125
4110
  current => {
4126
4111
  /** @type {?} */
4127
- const session = new NavigationSession.Active(this._navigationSessionContext, false, this.router.routerState.snapshot.url);
4112
+ const session = new NavigationState.NavigationTransition(this._navigationSessionContext, false, this.router.routerState.snapshot.url);
4128
4113
  session.storeVisit(visit);
4129
4114
  return session;
4130
4115
  }));
@@ -4134,7 +4119,7 @@ class PlaceRouter extends GarbageCollector {
4134
4119
  finally {
4135
4120
  // Router has finished (since there was no router change required) so we
4136
4121
  // need to end the navigation session.
4137
- if (this.navigationSession.active && !this.router.getCurrentNavigation()) {
4122
+ if (this.navigationState.isTransitional && !this.router.getCurrentNavigation()) {
4138
4123
  this.runStateTransition((/**
4139
4124
  * @param {?} session
4140
4125
  * @return {?}
@@ -4151,10 +4136,10 @@ class PlaceRouter extends GarbageCollector {
4151
4136
  */
4152
4137
  runStateTransition(transition) {
4153
4138
  /** @type {?} */
4154
- const previous = this._navigationSessionModel.value;
4139
+ const previous = this._navigationStateModel.value;
4155
4140
  /** @type {?} */
4156
- const next = transition(this.navigationSession);
4157
- this._navigationSessionModel.value = next;
4141
+ const next = transition(this.navigationState);
4142
+ this._navigationStateModel.value = next;
4158
4143
  if (next !== previous) {
4159
4144
  previous.dispose();
4160
4145
  Logger.get(this).info(`Router State Transition: ${previous.toString()} -> ${next.toString()}`);
@@ -4172,50 +4157,6 @@ class PlaceRouter extends GarbageCollector {
4172
4157
  [def.getFormattedRouteId(visit), def.getFormattedRouteParameters(visit)] :
4173
4158
  [def.getFormattedRouteParameters(visit)];
4174
4159
  }
4175
- // private onAngularRouterStarted(event: NavigationStart) {
4176
- // if (!this.navigationSession) {
4177
- // // We been activated by an external route rather than placeRouter.go(visit)
4178
- // this._navigationSessionModel.value = this.createExternalNavigationSession(event);
4179
- // }
4180
- // this.firstRoute = false;
4181
- // }
4182
- //
4183
- // private createExternalNavigationSession(event: NavigationStart) {
4184
- // return new NavigationSession.Active(
4185
- // this.modalInteractionService,
4186
- // this.angularLocation,
4187
- // // event.url,
4188
- // event.navigationTrigger === 'popstate'
4189
- // );
4190
- // }
4191
- // private onAngularRouterFinished(cancelled: boolean) {
4192
- // const session = this._navigationSessionModel.value;
4193
- // if (session.backClickedDuringCanDeactivateInteraction) {
4194
- // // we swallow this finished event but keep the session alive as we're going to
4195
- // // get another route started event, which will trigger anohter canDeactivate dialog
4196
- // // if we start a new session.
4197
- // // session.resetInteractionSession()
4198
- // } else {
4199
- // if (!cancelled) {
4200
- // const visits = session.getVisits();
4201
- // visits.forEach(v => this.placeHistory.add(v));
4202
- // // Update visits before we end the navigation session. This allows the placeOutets to
4203
- // // ignore visit changes that occur while the navigation is in progress
4204
- // this._activeVisits.value = visits;
4205
- // } else {
4206
- // // TODO: move this to the navigation session
4207
- // // Angular doesn't preserve the url when a guard cancels the back button.
4208
- // // See https://github.com/angular/angular/issues/13586#issuecomment-432795720
4209
- // // session.rememberPopStateReturnUrl(this.router.routerState.snapshot.url);
4210
- // if (session.isPopState) {
4211
- // console.log('cancelled during popstate');
4212
- // // this.angularLocation.go(session.previousUrl);
4213
- // }
4214
- // }
4215
- // session.dispose();
4216
- // this._navigationSessionModel.value = null;
4217
- // }
4218
- // }
4219
4160
  /**
4220
4161
  * @param {?} activatedRoute
4221
4162
  * @return {?}
@@ -4228,11 +4169,71 @@ class PlaceRouter extends GarbageCollector {
4228
4169
  child => child.url)));
4229
4170
  }
4230
4171
  /**
4231
- * @param {?} snapshot
4172
+ * @param {?} url
4173
+ * @return {?}
4174
+ */
4175
+ parseUrl(url) {
4176
+ return new UrlSnapshot(this.urlSerializer, url);
4177
+ }
4178
+ /**
4179
+ * @param {?} url
4180
+ * @return {?}
4181
+ */
4182
+ resetBrowserLocation(url) {
4183
+ this.angularLocation.go(url);
4184
+ }
4185
+ /**
4186
+ * @return {?}
4187
+ */
4188
+ getCurrentRouterUrl() {
4189
+ return this.router.routerState ? this.router.routerState.snapshot.url : null;
4190
+ }
4191
+ /**
4192
+ * @param {?} url
4193
+ * @return {?}
4194
+ */
4195
+ getActiveInteractionIdsFromUrl(url) {
4196
+ return this.parseUrl(url).getInteractionIds();
4197
+ }
4198
+ // @Trace()
4199
+ /**
4200
+ * @param {?} url
4201
+ * @return {?}
4202
+ */
4203
+ hasActiveInteractionIds(url) {
4204
+ return this.getActiveInteractionIdsFromUrl(url).length > 0;
4205
+ }
4206
+ /**
4232
4207
  * @return {?}
4233
4208
  */
4234
- parseUrl(snapshot) {
4235
- return new UrlSnapshot(this.urlSerializer.parse(snapshot.url));
4209
+ syncInteractionIdsWithRouter() {
4210
+ assert.isFalsey(this.navigationInProgress.value); // Updating interaction routes during an existing navigation breaks all the things.
4211
+ // Updating interaction routes during an existing navigation breaks all the things.
4212
+ /** @type {?} */
4213
+ const currentIds = this.interactionService.activeInteractionContextIds.value;
4214
+ if (___default.isEqual(currentIds, this.getActiveInteractionIdsFromUrl(this.getCurrentRouterUrl()))) {
4215
+ console.log('activity ids were the same, skipping');
4216
+ }
4217
+ else {
4218
+ if (currentIds.length < 1) {
4219
+ this.router.navigate(['.', {
4220
+ outlets: {
4221
+ [UrlSnapshot.INTERACTION_ROUTER_OUTLET]: null
4222
+ }
4223
+ }], {
4224
+ replaceUrl: true // remove the interaction from the history.
4225
+ });
4226
+ }
4227
+ else {
4228
+ /** @type {?} */
4229
+ const urlSnapshot = this.parseUrl(this.getCurrentRouterUrl());
4230
+ this.router.navigate(['.', {
4231
+ outlets: {
4232
+ [UrlSnapshot.INTERACTION_ROUTER_OUTLET]: UrlSnapshot.createInteractionOutletRouterCommands(currentIds)
4233
+ }
4234
+ }]);
4235
+ }
4236
+ }
4236
4237
  }
4237
4238
  }
4238
4239
  PlaceRouter.decorators = [
@@ -4246,27 +4247,28 @@ PlaceRouter.ctorParameters = () => [
4246
4247
  { type: UrlSerializer },
4247
4248
  { type: Location },
4248
4249
  { type: PlaceHistory },
4249
- { type: ModalInteractionService }
4250
+ { type: InteractionService }
4250
4251
  ];
4251
- /** @nocollapse */ PlaceRouter.ngInjectableDef = ɵɵdefineInjectable({ factory: function PlaceRouter_Factory() { return new PlaceRouter(ɵɵinject(Router), ɵɵinject(UrlSerializer), ɵɵinject(Location), ɵɵinject(PlaceHistory), ɵɵinject(ModalInteractionService)); }, token: PlaceRouter, providedIn: "root" });
4252
+ /** @nocollapse */ PlaceRouter.ngInjectableDef = ɵɵdefineInjectable({ factory: function PlaceRouter_Factory() { return new PlaceRouter(ɵɵinject(Router), ɵɵinject(UrlSerializer), ɵɵinject(Location), ɵɵinject(PlaceHistory), ɵɵinject(InteractionService)); }, token: PlaceRouter, providedIn: "root" });
4253
+ __decorate([
4254
+ Trace(),
4255
+ __metadata("design:type", Function),
4256
+ __metadata("design:paramtypes", []),
4257
+ __metadata("design:returntype", void 0)
4258
+ ], PlaceRouter.prototype, "syncInteractionIdsWithRouter", null);
4252
4259
  if (false) {
4253
4260
  /**
4254
4261
  * @type {?}
4255
4262
  * @private
4256
4263
  */
4257
- PlaceRouter.prototype.firstRoute;
4258
- /**
4259
- * @type {?}
4260
- * @private
4261
- */
4262
- PlaceRouter.prototype._navigationSessionModel;
4264
+ PlaceRouter.prototype._navigationStateModel;
4263
4265
  /**
4264
4266
  * @type {?}
4265
4267
  * @private
4266
4268
  */
4267
4269
  PlaceRouter.prototype._activeVisits;
4268
4270
  /** @type {?} */
4269
- PlaceRouter.prototype.navigationSessionActive;
4271
+ PlaceRouter.prototype.navigationInProgress;
4270
4272
  /** @type {?} */
4271
4273
  PlaceRouter.prototype.activeVisitIndex;
4272
4274
  /**
@@ -4274,6 +4276,11 @@ if (false) {
4274
4276
  * @private
4275
4277
  */
4276
4278
  PlaceRouter.prototype._navigationSessionContext;
4279
+ /**
4280
+ * @type {?}
4281
+ * @private
4282
+ */
4283
+ PlaceRouter.prototype._navigationStateTypeModel;
4277
4284
  /**
4278
4285
  * @type {?}
4279
4286
  * @private
@@ -4298,65 +4305,8 @@ if (false) {
4298
4305
  * @type {?}
4299
4306
  * @private
4300
4307
  */
4301
- PlaceRouter.prototype.modalInteractionService;
4308
+ PlaceRouter.prototype.interactionService;
4302
4309
  }
4303
- (function (PlaceRouter) {
4304
- PlaceRouter.INTERACTION_ROUTER_OUTLET = 'aup-interaction';
4305
- class InteractionRouteMediator {
4306
- /**
4307
- * @param {?} navigationSessionModelActive
4308
- * @param {?} router
4309
- */
4310
- constructor(navigationSessionModelActive, router) {
4311
- this.navigationSessionModelActive = navigationSessionModelActive;
4312
- this.router = router;
4313
- }
4314
- /**
4315
- * @return {?}
4316
- */
4317
- get isNavigating() {
4318
- return this.navigationSessionModelActive.value;
4319
- }
4320
- // If we're not in a navigation we push
4321
- // @Trace()
4322
- /**
4323
- * @return {?}
4324
- */
4325
- onActivityStarted() {
4326
- if (!this.isNavigating) {
4327
- this.router.navigate(['.', {
4328
- outlets: {
4329
- [PlaceRouter.INTERACTION_ROUTER_OUTLET]: ['modal'] // "open" must be a valid route for this outlet.
4330
- }
4331
- }], {
4332
- replaceUrl: false,
4333
- });
4334
- }
4335
- }
4336
- // @Trace()
4337
- /**
4338
- * @return {?}
4339
- */
4340
- onActivityFinished() {
4341
- if (!this.isNavigating) {
4342
- this.router.navigate(['.', {
4343
- outlets: {
4344
- [PlaceRouter.INTERACTION_ROUTER_OUTLET]: null
4345
- }
4346
- }], {
4347
- replaceUrl: true // remove the interaction from the history.
4348
- });
4349
- }
4350
- }
4351
- }
4352
- PlaceRouter.InteractionRouteMediator = InteractionRouteMediator;
4353
- if (false) {
4354
- /** @type {?} */
4355
- InteractionRouteMediator.prototype.navigationSessionModelActive;
4356
- /** @type {?} */
4357
- InteractionRouteMediator.prototype.router;
4358
- }
4359
- })(PlaceRouter || (PlaceRouter = {}));
4360
4310
 
4361
4311
  /**
4362
4312
  * @fileoverview added by tsickle
@@ -4450,9 +4400,9 @@ class PlaceOutletComponent extends DisposableComponent {
4450
4400
  this.placeChanged = new EventEmitter();
4451
4401
  this._activePlace = new MutableValueModel();
4452
4402
  this._activePlaceVisitModel = new DelegatingValueModel();
4453
- this._inOutletActivation = new Guard$1();
4454
- this._inOutletDeactivation = new Guard$1();
4455
- this._inRouteVisitUpdate = new Guard$1();
4403
+ this._inOutletActivation = new Guard();
4404
+ this._inOutletDeactivation = new Guard();
4405
+ this._inRouteVisitUpdate = new Guard();
4456
4406
  this._activatedRouteModel = new MutableValueModel();
4457
4407
  this._placeDefinition = new MutableValueModel();
4458
4408
  this.initialPlaceIndex = null;
@@ -4512,10 +4462,10 @@ class PlaceOutletComponent extends DisposableComponent {
4512
4462
  (next, previous) => {
4513
4463
  this.pushVisitChangesToRoute(next, previous);
4514
4464
  }), {
4515
- unless: this.placeRouter.navigationSessionActive
4465
+ unless: this.placeRouter.navigationInProgress
4516
4466
  });
4517
4467
  chain(this._activePlace)
4518
- .postponeWhile(placeRouter.navigationSessionActive)
4468
+ .postponeWhile(placeRouter.navigationInProgress)
4519
4469
  .subscribe((/**
4520
4470
  * @param {?} place
4521
4471
  * @return {?}
@@ -5435,6 +5385,201 @@ if (false) {
5435
5385
  ActivityOutletContext.prototype.componentReady = function (component) { };
5436
5386
  }
5437
5387
 
5388
+ /**
5389
+ * @fileoverview added by tsickle
5390
+ * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
5391
+ */
5392
+ class DialogInteractionContext extends InteractionContextBase {
5393
+ /**
5394
+ * @param {?} dialogService
5395
+ * @param {?} config
5396
+ */
5397
+ constructor(dialogService, config) {
5398
+ super();
5399
+ this.dialogService = dialogService;
5400
+ this.config = config;
5401
+ this._activeModel = new MutableValueModel(false);
5402
+ assert$1.notNil(dialogService);
5403
+ this.onDispose((/**
5404
+ * @return {?}
5405
+ */
5406
+ () => {
5407
+ if (this.isActive()) {
5408
+ lang.illegalState('Dispose called while active.');
5409
+ }
5410
+ }));
5411
+ }
5412
+ /**
5413
+ * @return {?}
5414
+ */
5415
+ get active() {
5416
+ return this._activeModel.readonly;
5417
+ }
5418
+ /**
5419
+ * @protected
5420
+ * @template D, R, E
5421
+ * @param {?} activityType
5422
+ * @param {?} data
5423
+ * @param {?=} disableClose
5424
+ * @return {?}
5425
+ */
5426
+ _startActivity(activityType, data, disableClose = true) {
5427
+ if (this.isActive()) {
5428
+ lang.illegalState(`Activity already in progress: ${this.activityList.value.map((/**
5429
+ * @param {?} a
5430
+ * @return {?}
5431
+ */
5432
+ a => a.constructor.name)).join(', ')}`);
5433
+ }
5434
+ this._activeModel.value = true;
5435
+ /** @type {?} */
5436
+ const config = Object.assign({}, this.config, {
5437
+ data,
5438
+ disableClose,
5439
+ panelClass: 'dialog-interaction-context'
5440
+ });
5441
+ /** @type {?} */
5442
+ const self = this;
5443
+ /** @type {?} */
5444
+ const matDialogRef = (/** @type {?} */ (this.dialogService.open(ActivityContainerComponent, config)));
5445
+ return new Promise((/**
5446
+ * @param {?} resolve
5447
+ * @param {?} reject
5448
+ * @return {?}
5449
+ */
5450
+ (resolve, reject) => {
5451
+ /** @type {?} */
5452
+ const activityContainer = matDialogRef.componentInstance;
5453
+ self.safelyUpdateActivityListDelegate(activityContainer.activityList);
5454
+ activityContainer.initialActivityOutletContext = {
5455
+ activityClass: activityType,
5456
+ activityData: data,
5457
+ /**
5458
+ * @param {?} result
5459
+ * @return {?}
5460
+ */
5461
+ onDone(result) {
5462
+ resolve(result);
5463
+ matDialogRef.close(true); // return true to let the after close listener know we've already handled it.
5464
+ },
5465
+ /**
5466
+ * @param {?} error
5467
+ * @return {?}
5468
+ */
5469
+ onCancel(error) {
5470
+ reject(error);
5471
+ matDialogRef.close(true); // return true to let the after close listener know we've already handled it.
5472
+ }
5473
+ };
5474
+ // we need to check if our onDone/onCancel methods above we called or if we were
5475
+ // closed by the user clicking the backdrop. If the later then we need to reject
5476
+ // our promise.
5477
+ matDialogRef.afterClosed().subscribe((/**
5478
+ * @param {?} promiseAlreadyFinished
5479
+ * @return {?}
5480
+ */
5481
+ promiseAlreadyFinished => {
5482
+ if (!promiseAlreadyFinished) {
5483
+ reject('auto-closed');
5484
+ }
5485
+ }));
5486
+ matDialogRef.updateSize();
5487
+ matDialogRef.afterOpened().subscribe((/**
5488
+ * @param {?} promiseAlreadyFinished
5489
+ * @return {?}
5490
+ */
5491
+ promiseAlreadyFinished => {
5492
+ matDialogRef.updateSize();
5493
+ }));
5494
+ })).finally((/**
5495
+ * @return {?}
5496
+ */
5497
+ () => {
5498
+ self.safelyUpdateActivityListDelegate(null);
5499
+ this._activeModel.value = false;
5500
+ }));
5501
+ }
5502
+ /**
5503
+ * Updates teh delegate on the next tick to avoid modifying state during the current change detection cycle.
5504
+ * @param {?} delegate
5505
+ * @return {?}
5506
+ */
5507
+ safelyUpdateActivityListDelegate(delegate) {
5508
+ setTimeout((/**
5509
+ * @return {?}
5510
+ */
5511
+ () => this.setActivityList(delegate)));
5512
+ }
5513
+ }
5514
+ if (false) {
5515
+ /**
5516
+ * @type {?}
5517
+ * @private
5518
+ */
5519
+ DialogInteractionContext.prototype._activeModel;
5520
+ /**
5521
+ * @type {?}
5522
+ * @private
5523
+ */
5524
+ DialogInteractionContext.prototype.dialogService;
5525
+ /** @type {?} */
5526
+ DialogInteractionContext.prototype.config;
5527
+ }
5528
+
5529
+ /**
5530
+ * @fileoverview added by tsickle
5531
+ * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
5532
+ */
5533
+ /** @type {?} */
5534
+ const DIALOG_INTERACTION_SERVICE_DEFAULTS = new InjectionToken('DIALOG_INTERACTION_SERVICE_DEFAULTS');
5535
+ class DialogInteractionContextFactory extends ModalInteractionContextFactory {
5536
+ /**
5537
+ * @param {?} dialogService
5538
+ * @param {?} dialogServiceDefaults
5539
+ * @param {?} matDialogDefaultConfig
5540
+ */
5541
+ constructor(dialogService, dialogServiceDefaults, matDialogDefaultConfig) {
5542
+ super();
5543
+ this.dialogService = dialogService;
5544
+ this.dialogServiceDefaults = dialogServiceDefaults;
5545
+ this.matDialogDefaultConfig = matDialogDefaultConfig;
5546
+ assert$1.notNil(dialogService);
5547
+ }
5548
+ /**
5549
+ * @return {?}
5550
+ */
5551
+ createInteractionContext() {
5552
+ /** @type {?} */
5553
+ const config = Object.assign({ autoFocus: false, hasBackdrop: true, closeOnNavigation: false }, this.matDialogDefaultConfig, this.dialogServiceDefaults);
5554
+ return new DialogInteractionContext(this.dialogService, config);
5555
+ }
5556
+ }
5557
+ DialogInteractionContextFactory.decorators = [
5558
+ { type: Injectable, args: [{
5559
+ providedIn: 'root'
5560
+ },] }
5561
+ ];
5562
+ /** @nocollapse */
5563
+ DialogInteractionContextFactory.ctorParameters = () => [
5564
+ { type: MatDialog },
5565
+ { type: MatDialogConfig, decorators: [{ type: Optional }, { type: Inject, args: [DIALOG_INTERACTION_SERVICE_DEFAULTS,] }] },
5566
+ { type: MatDialogConfig, decorators: [{ type: Optional }, { type: Inject, args: [MAT_DIALOG_DEFAULT_OPTIONS,] }] }
5567
+ ];
5568
+ /** @nocollapse */ DialogInteractionContextFactory.ngInjectableDef = ɵɵdefineInjectable({ factory: function DialogInteractionContextFactory_Factory() { return new DialogInteractionContextFactory(ɵɵinject(MatDialog$1), ɵɵinject(DIALOG_INTERACTION_SERVICE_DEFAULTS, 8), ɵɵinject(MAT_DIALOG_DEFAULT_OPTIONS, 8)); }, token: DialogInteractionContextFactory, providedIn: "root" });
5569
+ if (false) {
5570
+ /** @type {?} */
5571
+ DialogInteractionContextFactory.prototype.active;
5572
+ /**
5573
+ * @type {?}
5574
+ * @private
5575
+ */
5576
+ DialogInteractionContextFactory.prototype.dialogService;
5577
+ /** @type {?} */
5578
+ DialogInteractionContextFactory.prototype.dialogServiceDefaults;
5579
+ /** @type {?} */
5580
+ DialogInteractionContextFactory.prototype.matDialogDefaultConfig;
5581
+ }
5582
+
5438
5583
  /**
5439
5584
  * @fileoverview added by tsickle
5440
5585
  * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
@@ -5768,17 +5913,17 @@ class AbstractPlaceGuard {
5768
5913
  /** @type {?} */
5769
5914
  const parsedParams = placeDefinition.parseRouteParams(params);
5770
5915
  /** @type {?} */
5771
- const initialVisit = this.placeRouter.navigationSession.getVisitFor(placeDefinition) || new Visit(placeDefinition, parsedParams);
5916
+ const initialVisit = this.placeRouter.navigationState.getVisitFor(placeDefinition) || new Visit(placeDefinition, parsedParams);
5772
5917
  /** @type {?} */
5773
5918
  const sanitiser = new VisitSanitiser(activatedRoute, this.router, this.placeHistory, this.injector);
5774
5919
  /** @type {?} */
5775
5920
  const sanitisedVisit = yield sanitiser.sanitise(initialVisit.mergeRouteParameters(parsedParams));
5776
5921
  // Save the visit with any updated parameters. We need to save it so we remember any non route parameters
5777
- this.placeRouter.navigationSession.storeVisit(sanitisedVisit);
5922
+ this.placeRouter.navigationState.storeVisit(sanitisedVisit);
5778
5923
  if (initialVisit.hasRoutingChangedFrom(sanitisedVisit)) {
5779
5924
  // Regenerate the url
5780
5925
  /** @type {?} */
5781
- const commands = this.placeRouter.parseUrl(state).createRedirectCommandsFor(sanitisedVisit);
5926
+ const commands = this.placeRouter.parseUrl(state.url).createRedirectCommandsFor(sanitisedVisit);
5782
5927
  console.log('##### Place Guard Redirect', commands);
5783
5928
  return this.router.createUrlTree(commands, {
5784
5929
  replaceUrl: true,
@@ -5800,7 +5945,7 @@ class AbstractPlaceGuard {
5800
5945
  */
5801
5946
  canDeactivate(component, currentRoute, currentState, nextState) {
5802
5947
  return __awaiter(this, void 0, void 0, function* () {
5803
- return this.placeRouter.navigationSession.canDeactivatePlace(component, this.placeRouter.parseUrl(nextState));
5948
+ return this.placeRouter.navigationState.canDeactivatePlace(component, this.placeRouter.parseUrl(nextState.url));
5804
5949
  });
5805
5950
  }
5806
5951
  // @Trace()
@@ -5808,22 +5953,23 @@ class AbstractPlaceGuard {
5808
5953
  * @protected
5809
5954
  * @param {?} activatedRoute
5810
5955
  * @param {?} state
5811
- * @param {?} canActivate
5956
+ * @param {?} runPlaceGuards
5812
5957
  * @return {?}
5813
5958
  */
5814
- authorisePlaceThen(activatedRoute, state, canActivate) {
5959
+ authorisePlaceThen(activatedRoute, state, runPlaceGuards) {
5815
5960
  return __awaiter(this, void 0, void 0, function* () {
5816
5961
  if (PlaceComponent.isPlaceComponentConstructor(activatedRoute.component)) {
5817
5962
  /** @type {?} */
5818
5963
  const placeDefinition = PlaceComponent.getDefinition(activatedRoute.component);
5819
5964
  /** @type {?} */
5820
- const authorised = placeDefinition.authenticate ? yield this.isAuthorised(activatedRoute, state) : true;
5821
- if (authorised === true) {
5822
- return canActivate(placeDefinition);
5965
+ const authoriseResult = placeDefinition.authenticate ? yield this.isAuthorised(activatedRoute, state) : true;
5966
+ if (authoriseResult === true) {
5967
+ // we're authorised, now run the place guards.
5968
+ return runPlaceGuards(placeDefinition);
5823
5969
  }
5824
5970
  else {
5825
- console.log('not authorised result', authorised);
5826
- return authorised;
5971
+ console.log('not authorised result', authoriseResult);
5972
+ return authoriseResult;
5827
5973
  }
5828
5974
  }
5829
5975
  else {
@@ -5894,14 +6040,14 @@ class InteractionGuard {
5894
6040
  * @param {?} injector
5895
6041
  * @param {?} placeRouter
5896
6042
  * @param {?} angularLocation
5897
- * @param {?} modalInteractionService
6043
+ * @param {?} interactionService
5898
6044
  */
5899
- constructor(router, injector, placeRouter, angularLocation, modalInteractionService) {
6045
+ constructor(router, injector, placeRouter, angularLocation, interactionService) {
5900
6046
  this.router = router;
5901
6047
  this.injector = injector;
5902
6048
  this.placeRouter = placeRouter;
5903
6049
  this.angularLocation = angularLocation;
5904
- this.modalInteractionService = modalInteractionService;
6050
+ this.interactionService = interactionService;
5905
6051
  }
5906
6052
  /**
5907
6053
  * @param {?} route
@@ -5911,10 +6057,10 @@ class InteractionGuard {
5911
6057
  canActivate(route, state) {
5912
6058
  /** @type {?} */
5913
6059
  const url = this.router.parseUrl(state.url);
5914
- if (!this.modalInteractionService.isActive() && url.root.children[PlaceRouter.INTERACTION_ROUTER_OUTLET]) {
6060
+ if (!this.interactionService.isActive() && url.root.children[UrlSnapshot.INTERACTION_ROUTER_OUTLET]) {
5915
6061
  // This happens if we reload the page or the url was pasted as the route should only be activated
5916
6062
  // after the interaction context has become active.
5917
- delete url.root.children[PlaceRouter.INTERACTION_ROUTER_OUTLET];
6063
+ delete url.root.children[UrlSnapshot.INTERACTION_ROUTER_OUTLET];
5918
6064
  return url;
5919
6065
  }
5920
6066
  else {
@@ -5930,16 +6076,22 @@ class InteractionGuard {
5930
6076
  */
5931
6077
  canDeactivate(component, currentRoute, currentState, nextState) {
5932
6078
  return __awaiter(this, void 0, void 0, function* () {
5933
- /** @type {?} */
5934
- const popstateReturnUrl = this.placeRouter.navigationSession.startingUrl;
5935
- if (this.modalInteractionService.isActive()) {
5936
- // The activity is still active so the route change was triggered by the back button.
6079
+ if (this.interactionService.isActive()) {
6080
+ /** @type {?} */
6081
+ const currentIds = this.interactionService.activeInteractionContextIds.value;
5937
6082
  /** @type {?} */
5938
- const activity = yield this.modalInteractionService.getCurrentActivity();
5939
- activity.cancel();
5940
- // See ModalInteractionSession#onStart() for the url updating.
5941
- return false;
6083
+ const routeIds = this.placeRouter.getActiveInteractionIdsFromUrl(nextState.url);
6084
+ if (!isEqual(currentIds, routeIds)) {
6085
+ // The activity is still active so the route change was triggered by the back button.
6086
+ /** @type {?} */
6087
+ const activity = yield this.interactionService.getCurrentActivity();
6088
+ activity.cancel();
6089
+ }
5942
6090
  }
6091
+ // IMPORTANT:
6092
+ // We always return true, the router state engine will redirect as required. Return false
6093
+ // during the guard causes all kinds of grief. It might be worth trying a redirect here
6094
+ // again now that our state engine is more thorough.
5943
6095
  return true;
5944
6096
  });
5945
6097
  }
@@ -5955,9 +6107,9 @@ InteractionGuard.ctorParameters = () => [
5955
6107
  { type: Injector },
5956
6108
  { type: PlaceRouter },
5957
6109
  { type: Location },
5958
- { type: ModalInteractionService }
6110
+ { type: InteractionService }
5959
6111
  ];
5960
- /** @nocollapse */ InteractionGuard.ngInjectableDef = ɵɵdefineInjectable({ factory: function InteractionGuard_Factory() { return new InteractionGuard(ɵɵinject(Router), ɵɵinject(INJECTOR), ɵɵinject(PlaceRouter), ɵɵinject(Location), ɵɵinject(ModalInteractionService)); }, token: InteractionGuard, providedIn: "root" });
6112
+ /** @nocollapse */ InteractionGuard.ngInjectableDef = ɵɵdefineInjectable({ factory: function InteractionGuard_Factory() { return new InteractionGuard(ɵɵinject(Router), ɵɵinject(INJECTOR), ɵɵinject(PlaceRouter), ɵɵinject(Location), ɵɵinject(InteractionService)); }, token: InteractionGuard, providedIn: "root" });
5961
6113
  if (false) {
5962
6114
  /**
5963
6115
  * @type {?}
@@ -5983,7 +6135,7 @@ if (false) {
5983
6135
  * @type {?}
5984
6136
  * @private
5985
6137
  */
5986
- InteractionGuard.prototype.modalInteractionService;
6138
+ InteractionGuard.prototype.interactionService;
5987
6139
  }
5988
6140
 
5989
6141
  /**
@@ -6260,5 +6412,5 @@ if (false) {
6260
6412
  * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
6261
6413
  */
6262
6414
 
6263
- export { ACTIVITY_DATA, AUP_PLACE_CONFIG, AbstractActivity, AbstractInputComponent, AbstractPlaceGuard, AbstractPlaceNavigationComponent, Activity, ActivityContainerComponent, ActivityOutletComponent, AlertDialogComponent, AngularUiPowerupsModule, Bounds, BusyOverlayComponent, CommandDirective, ComponentsModule, ConfirmThenDialogComponent, ConfirmationDialogComponent, ConsolidatedParameterMap, DEFINITION_META_DATA_KEY, DIALOG_INTERACTION_SERVICE_DEFAULTS, DialogInteractionContext, DialogInteractionService, Dimension, DirectivesModule, DisposableComponent, EmptyStateComponent, FocusBindingDirective, Formatter, InplaceInteractionContextComponent, InteractionContext, InteractionContextBase, InteractionGuard, InteractionModule, InteractionOutletComponent, LEFT_RIGHT_PLACE_ANIMATION, ListPlaceNavComponent, ModalInteractionService, NavigationSession, NoopAuthGuard, NoopComponent, NumberInputComponent, ParameterDefinition, PasswordInputComponent, Place, PlaceComponent, PlaceComponentDeactivationHandler, PlaceDefinition, PlaceHistory, PlaceModule, PlaceOutletComponent, PlaceRouter, Point, ROUTE_PARAMETER_LIST_KEY, ResizeAwareComponent, RouteId, SelectInputComponent, StringInputComponent, TabbedPlaceNavigationComponent, UrlSnapshot, Visit, VisitParameter, VisitParameterList, VisitSanitiser, leftRightPlaceAnimation, slideDownAndUpAnimation, DirectivesModule as ɵa, CommandDirective as ɵb, ActivityContainerComponent as ɵba, InteractionContextBase as ɵbb, InteractionContext as ɵbc, ActivityOutletComponent as ɵbd, ConfirmationDialogComponent as ɵbe, AbstractActivity as ɵbf, ACTIVITY_DATA as ɵbg, Activity as ɵbh, ConfirmThenDialogComponent as ɵbj, AlertDialogComponent as ɵbk, InteractionOutletComponent as ɵbm, InplaceInteractionContextComponent as ɵbn, DIALOG_INTERACTION_SERVICE_DEFAULTS as ɵbo, DialogInteractionService as ɵbp, FocusBindingDirective as ɵc, DisposableComponent as ɵd, ComponentsModule as ɵe, NumberInputComponent as ɵf, AbstractInputComponent as ɵg, StringInputComponent as ɵh, PasswordInputComponent as ɵi, SelectInputComponent as ɵj, NoopComponent as ɵk, PlaceModule as ɵl, EmptyStateComponent as ɵm, BusyOverlayComponent as ɵn, PlaceOutletComponent as ɵo, leftRightPlaceAnimation as ɵp, LEFT_RIGHT_PLACE_ANIMATION as ɵq, AUP_PLACE_CONFIG as ɵr, PlaceRouter as ɵt, PlaceHistory as ɵu, ModalInteractionService as ɵv, TabbedPlaceNavigationComponent as ɵw, AbstractPlaceNavigationComponent as ɵx, ListPlaceNavComponent as ɵy, InteractionModule as ɵz };
6415
+ export { ACTIVITY_DATA, AUP_PLACE_CONFIG, AbstractActivity, AbstractInputComponent, AbstractPlaceGuard, AbstractPlaceNavigationComponent, Activity, ActivityContainerComponent, ActivityOutletComponent, AlertDialogComponent, AngularUiPowerupsModule, Bounds, BusyOverlayComponent, CommandDirective, ComponentsModule, ConfirmThenDialogComponent, ConfirmationDialogComponent, ConsolidatedParameterMap, DEFINITION_META_DATA_KEY, DIALOG_INTERACTION_SERVICE_DEFAULTS, DialogInteractionContext, DialogInteractionContextFactory, Dimension, DirectivesModule, DisposableComponent, EmptyStateComponent, FocusBindingDirective, Formatter, InplaceInteractionContextComponent, InteractionContext, InteractionContextBase, InteractionGuard, InteractionModule, InteractionOutletComponent, InteractionService, LEFT_RIGHT_PLACE_ANIMATION, ListPlaceNavComponent, ModalInteractionContextFactory, NavigationState, NoopAuthGuard, NoopComponent, NumberInputComponent, ParameterDefinition, PasswordInputComponent, Place, PlaceComponent, PlaceComponentDeactivationHandler, PlaceDefinition, PlaceHistory, PlaceModule, PlaceOutletComponent, PlaceRouter, Point, ROUTE_PARAMETER_LIST_KEY, ResizeAwareComponent, RouteId, SelectInputComponent, StringInputComponent, TabbedPlaceNavigationComponent, UrlSnapshot, Visit, VisitParameter, VisitParameterList, VisitSanitiser, leftRightPlaceAnimation, slideDownAndUpAnimation, DirectivesModule as ɵa, CommandDirective as ɵb, InteractionModule as ɵba, ActivityContainerComponent as ɵbb, InteractionContextBase as ɵbc, InteractionContext as ɵbd, ActivityOutletComponent as ɵbe, ConfirmationDialogComponent as ɵbf, AbstractActivity as ɵbg, ACTIVITY_DATA as ɵbh, Activity as ɵbi, ConfirmThenDialogComponent as ɵbk, AlertDialogComponent as ɵbl, InteractionOutletComponent as ɵbn, InplaceInteractionContextComponent as ɵbo, FocusBindingDirective as ɵc, DisposableComponent as ɵd, ComponentsModule as ɵe, NumberInputComponent as ɵf, AbstractInputComponent as ɵg, StringInputComponent as ɵh, PasswordInputComponent as ɵi, SelectInputComponent as ɵj, NoopComponent as ɵk, PlaceModule as ɵl, EmptyStateComponent as ɵm, BusyOverlayComponent as ɵn, PlaceOutletComponent as ɵo, leftRightPlaceAnimation as ɵp, LEFT_RIGHT_PLACE_ANIMATION as ɵq, AUP_PLACE_CONFIG as ɵr, PlaceRouter as ɵt, PlaceHistory as ɵu, InteractionService as ɵv, ModalInteractionContextFactory as ɵw, TabbedPlaceNavigationComponent as ɵx, AbstractPlaceNavigationComponent as ɵy, ListPlaceNavComponent as ɵz };
6264
6416
  //# sourceMappingURL=coolon-angular-ui-powerups.js.map