我有默认的 css 文件和单独的 css 文件,只有在满足某些条件时才应该应用(以 owerride 默认)。
我正在使用具有默认import 'file.css'
语法的create-react-app 。
决定是否动态加载特定 css 文件的最佳方法是什么?
我有默认的 css 文件和单独的 css 文件,只有在满足某些条件时才应该应用(以 owerride 默认)。
我正在使用具有默认import 'file.css'
语法的create-react-app 。
决定是否动态加载特定 css 文件的最佳方法是什么?
该require
方法仅在开发中有效(因为所有 CSS 都在构建时捆绑在一起),而该import
方法根本不起作用(使用 CRA 3.3 版)。
在我们的例子中,我们有多个不能捆绑的主题 - 所以我们使用React.lazy
and解决了这个问题React.Suspense
。
我们有ThemeSelector
,它有条件地加载正确的 css。
import React from 'react';
/**
* The theme components only imports it's theme CSS-file. These components are lazy
* loaded, to enable "code splitting" (in order to avoid the themes being bundled together)
*/
const Theme1 = React.lazy(() => import('./Theme1'));
const Theme2 = React.lazy(() => import('./Theme2'));
const ThemeSelector: React.FC = ({ children }) => (
<>
{/* Conditionally render theme, based on the current client context */}
<React.Suspense fallback={() => null}>
{shouldRenderTheme1 && <Theme1 />}
{shouldRenderTheme2 && <Theme2 />}
</React.Suspense>
{/* Render children immediately! */}
{children}
</>
);
export default ThemeSelector;
该Theme
组件的唯一工作是导入正确的 css 文件:
import * as React from 'react';
// 👇 Only important line - as this component should be lazy-loaded,
// to enable code - splitting for this CSS.
import 'theme1.css';
const Theme1: React.FC = () => <></>;
export default Theme1;
本ThemeSelector
应包裹App
分量,在src/index.tsx
:
import React from 'react';
import ReactDOM from 'react-dom';
import ThemeSelector from 'themes/ThemeSelector';
ReactDOM.render(
<ThemeSelector>
<App />
</ThemeSelector>,
document.getElementById('root')
);
据我了解,这迫使每个Theme
都被拆分成单独的包(实际上也拆分了 CSS)。
正如评论中提到的,这个解决方案没有提供切换主题运行时的简单方法。此解决方案侧重于将主题拆分为单独的包。
如果您已经将主题拆分为单独的 CSS 文件,并且您想交换主题运行时,您可能需要查看使用的解决方案ReactHelmet
(如下面@Alexander Ladonin 的回答所示)
您可以改用require('file.css')
语法。这将允许您将其放入条件中。
例如
if(someCondition) {
require('file.css');
}
使用react头盔。它动态地将链接、元标记等添加到文档标题中。将其添加到任何渲染方法中。
import {Component} from 'react';
import ReactHelmet from 'react-helmet';
class Example extends Component{
render(
<ReactHelmet link={
[{"rel": "stylesheet", type:"text/css", "href": "/style.css"}]
}/>);
}
}
您可以在下一次<ReactHelmet/>
渲染时重写它。
其他解决方案对我不起作用。经过一天的搜索,我获得了以下解决方案。在我的问题中,我有两个用于 RTL 或 LTR 的 CSS 文件,例如app.rtl.css
或app.ltr.css
Style
像这样创建一个功能组件:
import React, { useState } from "react";
export default function Style(props) {
const [stylePath, setStylePath] = useState(props.path);
return (
<div>
<link rel="stylesheet" type="text/css" href={stylePath} />
</div>
);
}
然后你可以调用它,例如App.js
:
function App() {
...
return (
<Style path={`/css/app.${direction}.css`} />
)}
direction
param 包含rtl
或ltr
确定应该加载哪个文件。