chore(): sync with main

This commit is contained in:
Liam DeBeasi
2021-10-22 15:24:34 -04:00
92 changed files with 66506 additions and 19097 deletions

View File

@ -110,7 +110,7 @@ describe('View Stacks', () => {
const itemC = createRegisteredViewItem(viewStacks, 1, '/home/3', true);
const itemD = createRegisteredViewItem(viewStacks, 1, '/home/4', true);
viewStacks.unmountLeavingViews(1, itemA, itemD);
viewStacks.unmountLeavingViews(1, itemA, -3);
expect(itemB.mount).toEqual(false);
expect(itemB.ionPageElement).toEqual(undefined);
@ -127,7 +127,7 @@ describe('View Stacks', () => {
const itemC = createRegisteredViewItem(viewStacks);
const itemD = createRegisteredViewItem(viewStacks);
viewStacks.mountIntermediaryViews(1, itemD, itemA);
viewStacks.mountIntermediaryViews(1, itemA, 3);
expect(itemB.mount).toEqual(true);
expect(itemC.mount).toEqual(true);

View File

@ -105,11 +105,15 @@ export const createLocationHistory = () => {
const size = () => locationHistory.length;
const updateByHistoryPosition = (routeInfo: RouteInfo) => {
const updateByHistoryPosition = (routeInfo: RouteInfo, updateEntries: boolean) => {
const existingRouteIndex = locationHistory.findIndex(r => r.position === routeInfo.position);
if (existingRouteIndex === -1) return;
locationHistory[existingRouteIndex].pathname = routeInfo.pathname;
if (updateEntries) {
locationHistory[existingRouteIndex].pushedByRoute = routeInfo.pushedByRoute;
}
}
/**

View File

@ -258,6 +258,7 @@ export const createIonRouter = (opts: IonicVueRouterOptions, router: Router) =>
}
routeInfo.position = currentHistoryPosition;
routeInfo.delta = delta;
const historySize = locationHistory.size();
const historyDiff = currentHistoryPosition - initialHistoryPosition;
@ -271,7 +272,23 @@ export const createIonRouter = (opts: IonicVueRouterOptions, router: Router) =>
* new items within the stack.
*/
if (historySize > historyDiff && routeInfo.tab === undefined) {
locationHistory.updateByHistoryPosition(routeInfo);
/**
* When going from /a --> /a/1 --> /b, then going
* back to /a, then going /a --> /a/2 --> /b, clicking
* the ion-back-button should return us to /a/2, not /a/1.
* However, since the route entry for /b already exists,
* we need to update other information such as the "pushedByRoute"
* so we know which route pushed this new route.
*
* However, when using router.go with a stride of >1 or <-1,
* we should not update this additional information because
* we are traversing through the history, not pushing new states.
* Going from /a --> /b --> /c, then doing router.go(-2), then doing
* router.go(2) to go from /a --> /c should not update the route
* listing to say that /c was pushed by /a.
*/
const hasDeltaStride = delta !== undefined && Math.abs(delta) !== 1;
locationHistory.updateByHistoryPosition(routeInfo, !hasDeltaStride);
} else {
locationHistory.add(routeInfo);
}

View File

@ -27,6 +27,7 @@ export interface RouteInfo {
pushedByRoute?: string;
tab?: string;
position?: number;
delta?: number;
}
export interface RouteParams {

View File

@ -148,34 +148,6 @@ export const createViewStacks = (router: Router) => {
return [];
}
/**
* Given a view stack and entering/leaving views,
* determine the position of each item in the stack.
* This is useful for removing/adding views in between
* the view items when navigating using router.go.
* Use this method instead of doing an `Array.findIndex`
* for both view items.
*/
const findViewIndex = (viewStack: ViewItem[], enteringViewItem: ViewItem, leavingViewItem: ViewItem) => {
let enteringIndex = -1;
let leavingIndex = -1;
for (let i = 0; i <= viewStack.length - 1; i++) {
const viewItem = viewStack[i];
if (viewItem === enteringViewItem) {
enteringIndex = i;
} else if (viewItem === leavingViewItem) {
leavingIndex = i;
}
if (enteringIndex > -1 && leavingIndex > -1) {
break;
}
}
return { enteringIndex, leavingIndex };
}
/**
* When navigating backwards, we need to clean up and
* leaving pages so that they are re-created if
@ -183,13 +155,13 @@ export const createViewStacks = (router: Router) => {
* important when using router.go and stepping back
* multiple pages at a time.
*/
const unmountLeavingViews = (outletId: number, enteringViewItem: ViewItem, leavingViewItem: ViewItem) => {
const unmountLeavingViews = (outletId: number, viewItem: ViewItem, delta: number = 1) => {
const viewStack = viewStacks[outletId];
if (!viewStack) return;
const { enteringIndex: startIndex, leavingIndex: endIndex } = findViewIndex(viewStack, enteringViewItem, leavingViewItem);
const startIndex = viewStack.findIndex(v => v === viewItem);
for (let i = startIndex + 1; i < endIndex; i++) {
for (let i = startIndex + 1; i < startIndex - delta; i++) {
const viewItem = viewStack[i];
viewItem.mount = false;
viewItem.ionPageElement = undefined;
@ -203,14 +175,26 @@ export const createViewStacks = (router: Router) => {
* developers to step forward over multiple views.
* The intermediary views need to be remounted so that
* swipe to go back works properly.
* We need to account for the delta value here too because
* we do not want to remount an unrelated view.
* Example:
* /home --> /page2 --> router.back() --> /page3
* Going to /page3 would remount /page2 since we do
* not prune /page2 from the stack. However, /page2
* needs to remain in the stack.
* Example:
* /home --> /page2 --> /page3 --> router.go(-2) --> router.go(2)
* We would end up on /page3, but users need to be able to swipe
* to go back to /page2 and /home, so we need both pages mounted
* in the DOM.
*/
const mountIntermediaryViews = (outletId: number, enteringViewItem: ViewItem, leavingViewItem: ViewItem) => {
const mountIntermediaryViews = (outletId: number, viewItem: ViewItem, delta: number = 1) => {
const viewStack = viewStacks[outletId];
if (!viewStack) return;
const { enteringIndex: endIndex, leavingIndex: startIndex } = findViewIndex(viewStack, enteringViewItem, leavingViewItem);
const startIndex = viewStack.findIndex(v => v === viewItem);
for (let i = startIndex + 1; i < endIndex; i++) {
for (let i = startIndex + 1; i < startIndex + delta; i++) {
viewStack[i].mount = true;
}
}