在 React 路由器 5 中使用变量(不是静态组件)将 props 传递给组件
Passing props to a component using a variable (not a static component) in React router 5
我知道在 react-router 5 中你可以像这样将一些 props 传递给子组件:
<Route path="/"
exact
render={ props => <MyPage title={myTitle} dataPath={myDataPath}
{...props} />} />
但就我而言,我使用的是路由模型:
import { ComponentType, FC } from "react";
interface RouteItem {
key: string;
title: string;
tooltip?: string;
path?: string;
component?: FC<{}>;
contentPath?: string;
enabled: boolean;
icon?: ComponentType;
subRoutes?: Array<RouteItem>;
appendDivider?: boolean;
}
export default RouteItem;
然后我在配置文件 (config/index.ts
) 中定义它们,如下所示:
// components
import DetailPageTemplate from "../pages/DetailPageTemplate";
// interface
import RouteItem from '../model/RouteItem.model';
// define app routes
export const routes: Array<RouteItem> = [
{
key: "router-detail-one",
title: "Detail One",
path: "/detail-one",
enabled: true,
contentPath: '../data/DetailOneCopy.json',
component: DetailPageTemplate,
appendDivider: true,
},
{
key: "router-detail-two",
title: "Detail Two",
path: "/detail-two",
enabled: true,
contentPath: '../data/DetailTwoCopy.json',
component: DetailPageTemplate,
appendDivider: true,
},
];
这感觉像是一个非常愚蠢的问题(我不熟悉语法)但我希望能够在我的 App.tsx 中循环传递其中一些参数,但我不知道如何将道具传递给组件变量(因为它不是 JSX):
import React from 'react';
// components
import Layout from './components/global/Layout';
import { BrowserRouter as Router, Switch, Route } from 'react-router-dom';
// app routes
import { routes } from './config';
// interfaces
import RouteItem from './model/RouteItem.model';
// define app context
const AppContext = React.createContext(null);
// default component
const DefaultComponent = () => <div>No Component Defined.</div>;
function App() {
// const [useDefaultTheme, toggle] = useReduc
return (
<>
<AppContext.Provider value={null}>
<Router>
<Switch>
<Layout>
{routes.map((route: RouteItem) =>
(
<Route
key={`${route.key}`}
path={`${route.path}`}
component={route.component || DefaultComponent}
{ /* ^ How can I pass props to the component? */ }
exact
/>
)
)}
</Layout>
</Switch>
</Router>
</ThemeProvider>
</AppContext.Provider>
</>
);
}
export default App;
我认为您可以将 route.component
用作 JSX <route.component />
但为了命名一致性(大写),您可以先将其分配给 const
{routes.map((route: RouteItem) => {
const Component = route.component;
return (
<Route
key={`${route.key}`}
path={`${route.path}`}
component={
(Component &&
((props: any) => <Component {...props} />)) ||
DefaultComponent
}
exact
/>
);
})}
https://codesandbox.io/s/react-router-dom-typescript-dynamic-component-s7n72?file=/src/index.tsx
我知道在 react-router 5 中你可以像这样将一些 props 传递给子组件:
<Route path="/"
exact
render={ props => <MyPage title={myTitle} dataPath={myDataPath}
{...props} />} />
但就我而言,我使用的是路由模型:
import { ComponentType, FC } from "react";
interface RouteItem {
key: string;
title: string;
tooltip?: string;
path?: string;
component?: FC<{}>;
contentPath?: string;
enabled: boolean;
icon?: ComponentType;
subRoutes?: Array<RouteItem>;
appendDivider?: boolean;
}
export default RouteItem;
然后我在配置文件 (config/index.ts
) 中定义它们,如下所示:
// components
import DetailPageTemplate from "../pages/DetailPageTemplate";
// interface
import RouteItem from '../model/RouteItem.model';
// define app routes
export const routes: Array<RouteItem> = [
{
key: "router-detail-one",
title: "Detail One",
path: "/detail-one",
enabled: true,
contentPath: '../data/DetailOneCopy.json',
component: DetailPageTemplate,
appendDivider: true,
},
{
key: "router-detail-two",
title: "Detail Two",
path: "/detail-two",
enabled: true,
contentPath: '../data/DetailTwoCopy.json',
component: DetailPageTemplate,
appendDivider: true,
},
];
这感觉像是一个非常愚蠢的问题(我不熟悉语法)但我希望能够在我的 App.tsx 中循环传递其中一些参数,但我不知道如何将道具传递给组件变量(因为它不是 JSX):
import React from 'react';
// components
import Layout from './components/global/Layout';
import { BrowserRouter as Router, Switch, Route } from 'react-router-dom';
// app routes
import { routes } from './config';
// interfaces
import RouteItem from './model/RouteItem.model';
// define app context
const AppContext = React.createContext(null);
// default component
const DefaultComponent = () => <div>No Component Defined.</div>;
function App() {
// const [useDefaultTheme, toggle] = useReduc
return (
<>
<AppContext.Provider value={null}>
<Router>
<Switch>
<Layout>
{routes.map((route: RouteItem) =>
(
<Route
key={`${route.key}`}
path={`${route.path}`}
component={route.component || DefaultComponent}
{ /* ^ How can I pass props to the component? */ }
exact
/>
)
)}
</Layout>
</Switch>
</Router>
</ThemeProvider>
</AppContext.Provider>
</>
);
}
export default App;
我认为您可以将 route.component
用作 JSX <route.component />
但为了命名一致性(大写),您可以先将其分配给 const
{routes.map((route: RouteItem) => {
const Component = route.component;
return (
<Route
key={`${route.key}`}
path={`${route.path}`}
component={
(Component &&
((props: any) => <Component {...props} />)) ||
DefaultComponent
}
exact
/>
);
})}
https://codesandbox.io/s/react-router-dom-typescript-dynamic-component-s7n72?file=/src/index.tsx