fix(react): fixng ion-router-outlet ref regresssion (#21786)

This commit is contained in:
Ely Lucas
2020-07-21 08:48:25 -06:00
committed by GitHub
parent dbe6853884
commit f4a08b7ed4
9 changed files with 72 additions and 5 deletions

View File

@@ -55,7 +55,6 @@ export class StackManager extends React.PureComponent<StackManagerProps, StackMa
}
async handlePageTransition(routeInfo: RouteInfo) {
// let shouldReRender = false;
// If routerOutlet isn't quite ready, give it another try in a moment
if (!this.routerOutletElement || !this.routerOutletElement.commit) {
@@ -172,6 +171,7 @@ export class StackManager extends React.PureComponent<StackManagerProps, StackMa
() => {
this.forceUpdate();
});
return (
<StackContext.Provider value={this.stackContextValue}>
{React.cloneElement(ionRouterOutlet as any, {
@@ -179,6 +179,9 @@ export class StackManager extends React.PureComponent<StackManagerProps, StackMa
if (ionRouterOutlet.props.setRef) {
ionRouterOutlet.props.setRef(node);
}
if (ionRouterOutlet.props.forwardedRef) {
ionRouterOutlet.props.forwardedRef.current = node;
}
this.routerOutletElement = node;
const { ref } = ionRouterOutlet as any;
if (typeof ref === 'function') {

View File

@@ -3,7 +3,7 @@ cd ../../react
npm run build
npm pack
cd ../react-router/test-app
npm i ../../react/ionic-react-5.2.2.tgz
npm i ../../react/ionic-react-5.2.3.tgz
npm run start

View File

@@ -0,0 +1,14 @@
const port = 3000;
describe('Multiple Tabs', () => {
/*
This spec tests that setting a ref on an IonRouterOutlet works
*/
it('/outlet-ref, page should contain the id of the ion-router-outlet', () => {
cy.visit(`http://localhost:${port}/outlet-ref`)
cy.get('div').contains('main-outlet')
cy.ionPageVisible('main')
})
})

View File

@@ -33,6 +33,7 @@ import NestedOutlet from './pages/nested-outlet/NestedOutlet';
import NestedOutlet2 from './pages/nested-outlet/NestedOutlet2';
import ReplaceAction from './pages/replace-action/Replace';
import TabsContext from './pages/tab-context/TabContext';
import { OutletRef } from './pages/outlet-ref/OutletRef';
debugger;
const App: React.FC = () => {
return (
@@ -47,6 +48,7 @@ const App: React.FC = () => {
<Route path="/nested-outlet2" component={NestedOutlet2} />
<Route path="/replace-action" component={ReplaceAction} />
<Route path="/tab-context" component={TabsContext} />
<Route path="/outlet-ref" component={OutletRef} />
</IonReactRouter>
</IonApp>
);

View File

@@ -38,6 +38,9 @@ const Main: React.FC<MainProps> = () => {
<IonItem routerLink="/tab-context">
<IonLabel>Tab Context</IonLabel>
</IonItem>
<IonItem routerLink="/outlet-ref">
<IonLabel>Outlet Ref</IonLabel>
</IonItem>
</IonList>
</IonContent>
</IonPage>

View File

@@ -0,0 +1,42 @@
import React, { useRef, useEffect } from 'react';
import { IonRouterOutlet, IonPage, IonHeader, IonToolbar, IonTitle, IonContent } from '@ionic/react';
import { Route } from 'react-router';
interface OutletRefProps {
}
export const OutletRef: React.FC<OutletRefProps> = () => {
const ref = useRef<HTMLIonRouterOutletElement>(null);
useEffect(() => {
console.log(ref);
}, []);
return (
<IonRouterOutlet id="main-outlet" ref={ref}>
<Route path="/outlet-ref" render={() => {
return <Main outletId={ref.current?.id} />;
}} />
</IonRouterOutlet>
);
};
const Main: React.FC<{ outletId?: string; }> = ({ outletId }) => {
return (
<IonPage data-pageid="main">
<IonHeader>
<IonToolbar>
<IonTitle>Main</IonTitle>
</IonToolbar>
</IonHeader>
<IonContent>
<div>{outletId}</div>
</IonContent>
</IonPage>
);
};
export default Main;

View File

@@ -46,7 +46,7 @@ class IonRouterOutletContainer extends React.Component<InternalProps, InternalSt
</OutletPageManager>
) : (
<StackManager routeInfo={this.context.routeInfo}>
<IonRouterOutletInner {...props}>
<IonRouterOutletInner {...props} forwardedRef={forwardedRef}>
{children}
</IonRouterOutletInner>
</StackManager>

View File

@@ -6,7 +6,10 @@ import { /*@__PURE__*/ createReactComponent } from './createComponent';
export const IonTabButtonInner = /*@__PURE__*/createReactComponent<JSX.IonTabButton & { onIonTabButtonClick?: (e: CustomEvent) => void; }, HTMLIonTabButtonElement>('ion-tab-button');
export const IonTabBarInner = /*@__PURE__*/createReactComponent<JSX.IonTabBar, HTMLIonTabBarElement>('ion-tab-bar');
export const IonBackButtonInner = /*@__PURE__*/createReactComponent<Omit<JSX.IonBackButton, 'icon'>, HTMLIonBackButtonElement>('ion-back-button');
export const IonRouterOutletInner = /*@__PURE__*/createReactComponent<JSX.IonRouterOutlet & { setRef?: (val: HTMLIonRouterOutletElement) => void; }, HTMLIonRouterOutletElement>('ion-router-outlet');
export const IonRouterOutletInner = /*@__PURE__*/createReactComponent<JSX.IonRouterOutlet & {
setRef?: (val: HTMLIonRouterOutletElement) => void;
forwardedRef?: React.RefObject<HTMLIonRouterOutletElement>;
}, HTMLIonRouterOutletElement>('ion-router-outlet');
// ionicons
export const IonIconInner = /*@__PURE__*/createReactComponent<IoniconsJSX.IonIcon, HTMLIonIconElement>('ion-icon');

View File

@@ -9,7 +9,7 @@ import { StackContext } from './StackContext';
interface OutletPageManagerProps {
className?: string;
forwardedRef?: React.RefObject<HTMLDivElement>;
forwardedRef?: React.RefObject<HTMLIonRouterOutletElement>;
routeInfo?: RouteInfo;
StackManager: any;
}