Material ui 使用基于选定主题模式的调色板原色

Posted

技术标签:

【中文标题】Material ui 使用基于选定主题模式的调色板原色【英文标题】:Material ui use palette primary color based on selected theme mode 【发布时间】:2022-01-07 08:16:53 【问题描述】:

在使用 mui react 时,我想使用我的主题主调色板中的颜色为一些使用 div 制作的非材质 ui 自定义组件着色。

我目前可以直接使用theme.palette.primary.main.light 颜色,包括用于文本颜色的theme.palette.text.primary

但是如果我将主题更改为深色模式,我还必须更改颜色参考,方法是使用如下条件检查 theme.mode

  <div
    style=
      backgroundColor:
        theme.palette.mode == "light"
          ? theme.palette.primary.dark
          : theme.palette.primary.light
    
  >
    Test
  </div>

那么有没有一种方法可以让我们像在材质 UI 组件中一样进行这项工作?传递theme.palette.primary 将与主题模式更改一起使用吗?

也许更简单一些,比如:

<div style= backgroundColor: theme.palette.primary ></div>

【问题讨论】:

【参考方案1】:

您可以使用Context 全局保存您的主题设置,还需要将lightdark 等主题分开。

// SettingsContext.js
import React, 
  createContext,
  useState
 from 'react';

const defaultSettings = 
  // you could add sort of global settings here
  theme: 'light'
;

const SettingsContext = createContext(
  settings: defaultSettings,
  saveSettings: () => 
);

export const SettingsProvider = ( settings, children ) => 
  const [currentSettings, setCurrentSettings] = useState(settings || defaultSettings);

  return (
    <SettingsContext.Provider
      value=
        settings: currentSettings,
      
    >
      children
    </SettingsContext.Provider>
  );
;

export const SettingsConsumer = SettingsContext.Consumer;

export default SettingsContext;

您可以将设置上下文构建为钩子,但您可以跳过它。

// useSettings.js
import  useContext  from 'react'; 
import SettingsContext from './SettingsContext';

const useSettings = () => useContext(SettingsContext);

export default useSettings;

然后尝试创建包含深色和浅色模式的自定义主题。

// theme.js
import  createTheme as createMuiTheme  from '@mui/material/styles';

const themes = 
  'light': 
    ...
  ,
  'dark': 
    ...
  
];

export const createTheme = (name) => 
  return createMuiTheme(themes[name]);

之后,您需要传递您在App.jsindex.js 任何***文件中选择的主题。

// App.js
...
import  ThemeProvider  from '@mui/material/styles';
import useSettings from './useSettings';
import  createTheme  from './theme.js';

const App = () => 
  const  settings  = useSettings();

  const theme = createTheme(settings.theme);

  return (
    <ThemeProvider theme=theme>
      ...
    </ThemeProvider>
  );
;

export default App;
...

就是这样。

现在您可以在组件中使用所选主题而无需条件渲染。

<div style= backgroundColor: theme.palette.primary ></div>

但这不会阻止硬刷新后选择的主题。

因此,如果您想在刷新浏览器后仍保持选中主题,则可以将主题设置保存在 localStorage 中。

【讨论】:

谢谢,那么,这是否意味着theme.palette.mode 中的mode 变量没有用?因为,如果我们在您的代码中将其设置为亮或暗,它无论如何都可以工作。正确的?或者它有什么用? @Abraham,是的,它有效。但有用的是分别为每个主题设置调色板。它将使您的代码简单易读,实际上用户可以手动更改主题。

以上是关于Material ui 使用基于选定主题模式的调色板原色的主要内容,如果未能解决你的问题,请参考以下文章

获取其他元素的 Angular Material 主题配色方案/调色板

React Material-UI 和颜色:警告

为啥我们有多个 Material UI 的颜色声明?

如何将材质调色板转换为 Flutter 主题?

如何添加自定义 MUI 调色板颜色

基于谷歌材料调色板的卡片样式