Material-UI 中使用 Styled-Components 的媒体查询
Posted
技术标签:
【中文标题】Material-UI 中使用 Styled-Components 的媒体查询【英文标题】:Media Queries in Material-UI Using Styled-Components 【发布时间】:2020-05-12 06:46:36 【问题描述】:Material UI 有一组不错的内置媒体查询:https://material-ui.com/customization/breakpoints/#css-media-queries
Material UI 还允许我们将 Styled-Components 与 Material UI 一起使用:https://material-ui.com/guides/interoperability/#styled-components
我想知道如何将两者结合在一起。也就是说,如何使用 Styled Components 和 Material-UI 的内置断点进行媒体查询?
谢谢。
更新:
这是我正在尝试做的一个示例:
import React, useState from 'react'
import styled from 'styled-components'
import
AppBar as MuiAppBar,
Drawer as MuiDrawer,
Toolbar,
from '@material-ui/core'
const drawerWidth = 240
const AdminLayout = ( children ) =>
return (
<BaseLayout>
<AppBar position="static">
<Toolbar>
TOOLBAR
</Toolbar>
</AppBar>
<Drawer>
DRAWER
</Drawer>
children
</BaseLayout>
)
AdminLayout.propTypes =
children: PropTypes.node.isRequired,
export default AdminLayout
// ------- STYLES -------
const AppBar = styled(MuiAppBar)`
/* Implement appBar styles from useStyles */
`
const Drawer = styled(MuiDrawer)`
/* Implement drawer styles from useStyles */
`
// STYLES THAT I WANT TO CONVERT TO STYLED-COMPONENTS
const useStyles = makeStyles(theme => (
root:
display: 'flex',
,
drawer:
[theme.breakpoints.up('sm')]:
width: drawerWidth,
flexShrink: 0,
,
,
appBar:
[theme.breakpoints.up('sm')]:
width: `calc(100% - $drawerWidthpx)`,
marginLeft: drawerWidth,
,
,
toolbar: theme.mixins.toolbar,
))
【问题讨论】:
theme.breakpoints.down('sm')
只是一个字符串'(min-width:600px)'
,在样式组件中使用它
这需要我对像素值进行硬编码——如果我想使用sm
变量怎么办?
什么?使用 theme.breakpoints.down('sm')
时无需硬编码
也许我没有关注。您介意向我展示一个如何在样式组件中使用theme.breakpoints.down('sm')
的示例吗?
做一个小例子,说明你在没有样式组件的情况下尝试使用 MU 设置样式,我将向你展示一个示例
【参考方案1】:
breakpoints are provided 作为默认主题的一部分。
它们是常量,不会改变,因此您可以在组件或样式主题中使用它们:
import React from 'react';
import styled from 'styled-components';
import makeStyles from '@material-ui/core/styles';
const useStyles = makeStyles(theme =>
console.log('md', theme.breakpoints.up('md'));
return ;
);
const BP =
MD: `@media (min-width:960px) `,
;
const Container = styled.div`
background-color: green;
$( bp ) => bp
background-color: red;
`;
export default function StyledComponentsButton()
useStyles();
return <Container bp=BP.MD>Example</Container>;
【讨论】:
感谢您的回答以及您为此付出的所有时间。不过,我很遗憾地说,但这不是我想要做的。对于初学者,const BP
硬编码md
断点的像素值。但我想使用theme.breakpoints
中的md
断点。其次,我不想依赖道具——我只想将媒体查询插入到样式化组件中。
我的问题是如何在 styled-component 中访问 theme.breakpoint。
如我多次提到的,使用风格化主题传递它【参考方案2】:
下面是一个示例,展示了一种利用带有样式组件的 Material-UI 主题断点的方法。这会将 Material-UI 主题传递给 styled-components ThemeProvider
,以使其可作为样式中的道具使用。该示例还使用 StylesProvider
和 injectFirst
属性,这样 Material-UI 样式将出现在 <head>
的开头而不是结尾,因此 styled-components 样式出现在 Material-UI 样式和因此,当特异性相同时获胜。
import React from "react";
import styled, ThemeProvider as SCThemeProvider from "styled-components";
import useTheme, StylesProvider from "@material-ui/core/styles";
import MuiAppBar from "@material-ui/core/AppBar";
const AppBar = styled(MuiAppBar)`
background-color: red;
$props => props.theme.breakpoints.up("sm")
background-color: orange;
$props => props.theme.breakpoints.up("md")
background-color: yellow;
color: black;
$props => props.theme.breakpoints.up("lg")
background-color: green;
color: white;
`;
export default function App()
const muiTheme = useTheme();
return (
<StylesProvider injectFirst>
<SCThemeProvider theme=muiTheme>
<AppBar>Sample AppBar</AppBar>
</SCThemeProvider>
</StylesProvider>
);
相关文档:
styled-components 主题用法:https://styled-components.com/docs/advanced#theming StylesProvider 注入第一:https://material-ui.com/styles/api/#stylesprovider【讨论】:
这样的东西对我有用: const GridBox = styled(Box)` $(theme) => ` display: grid;网格模板行:自动; $theme.breakpoints.up("sm") 网格模板列:5fr 3fr; ;
;
在我看来,这有太多的情感味道。我更喜欢 Mike Mathew 的不使用情感语法的解决方案。【参考方案3】:
如果您使用"Style Objects" approach(即“javascript”)来设置样式组件,那么这是实现相同结果的方法。这是建立在前面提到的 Ryan Cogswell 之上的。
如果从另一个 CSS-in-JS 系统(如 Material-UI 的内置 JSS)切换,有些人可能更喜欢这个。此外,“样式对象”方法只需要您引入一次props
,而不是在任何行上使用props
变量。有选择是好事。 ?
样式对象
const AppBar = styled(MuiAppBar)((props) => (
backgroundColor: red;
[props.theme.breakpoints.up("sm")]:
backgroundColor: orange,
,
[props.theme.breakpoints.up("md")]:
backgroundColor: yellow,
color: black,
,
[props.theme.breakpoints.up("lg")]:
backgroundColor: green,
color: white,
,
));
样式对象,但更简洁
由于我们只需要使用 JavaScript 方法访问一次道具,并且我们只在这个样式区域中使用主题,因此我们可以从传入的 props
中解构 theme
以减少代码。
const AppBar = styled(MuiAppBar)(( theme ) => (
backgroundColor: red;
[theme.breakpoints.up("sm")]:
backgroundColor: orange,
,
[theme.breakpoints.up("md")]:
backgroundColor: yellow,
color: black,
,
[theme.breakpoints.up("lg")]:
backgroundColor: green,
color: white,
,
));
注意:如果您使用的是 TypeScript,并且已将您的样式化组件主题设置为与 Material-UI 主题相匹配,那么无论是 CSS 还是 JavaScript 方法,类型安全仍然可以正常工作。
【讨论】:
以上是关于Material-UI 中使用 Styled-Components 的媒体查询的主要内容,如果未能解决你的问题,请参考以下文章
如何在 Material-UI 中使用 Box 组件覆盖按钮?