Trying to override the css of AppBar from React Material Ui, - css

<AppBar className={classes.header}/>
The suspect
const classes = useStyles();
const useStyles = makeStyles((theme: Theme) =>
createStyles({
header: {
borderTop: '10px',
borderTopColor: '#367BB5'
},
grow: {
flexGrow: 1
},
menuButton: {
marginRight: theme.spacing(2),
}
);
The grow, and menuButton styling came from the AppBar code directly from Material Ui, but I am trying to implement the header style into the AppBar, unsuccessfully, I have read the documentation but its not very clear to me.
export default Header;
EDIT:
The docs say that the Style sheet name: MuiAppBar but whenever I change header to that, it doesn't change anything
const useStyles = makeStyles({
root: {
position: 'static', // doesnt work
borderTop: '100px', // doesnt work
borderTopColor: '#367BB5', // doesnt work
backgroundColor: '#fafafa',
},
})
<AppBar position="static" classes={{ root: classes.root }}>
Doing this allows me to change the backgroundColor, but the other properties don't work. Not sure why

It's important that you follow this page: https://material-ui.com/customization/theming/
You need to use the ThemeProvider in order to custom the style.

Related

MUI KeyboardDatePicker change styles of date input box

Currently, I am trying to modify KeyboardDatePicker board color, size, font, padding, but unfortunately, all approaches don’t work. I tried so far:
1 . useStyles :
const useStyles = (params: any) =>
makeStyles(() =>
createStyles({
componentStyle: {
width: params.width ? params.width : 'auto',
color: params.color ? params.color : 'inherit',
verticalAlign: 'middle',
fontSize: '12px',
border: 'solid 2px #0070D8',
},
})
);
Doesn’t override and a border appears on current KeyboardDatePicker border, size doesn’t change as well.
2 . Theme provide, it overrides calendar theme, but not KeyboardDatePicker date box.
<ThemeProvider theme={theme}>
3 . Add styles into KeyboardDatePicker, it is the only working approach
style={{width:"246px",height:"44px"}}
How would you suggest modifying styles of KeyboardDatePicker, and yes style={} approach it's not the correct way to changes styles. p.s I am using Material-UI 4
My KeyboardDatesPicker:
<KeyboardDatePicker
format="MM/dd/yyyy"
margin="normal"
id="date-picker-inline"
defaultValue={props.value}
value={selectedDate}
required={props.required}
showTodayButton={true}
disableToolbar
inputVariant="outlined"
variant="inline"
onChange={(selectedDate) => setSelectedDate(selectedDate)}
KeyboardButtonProps={{
"aria-label": "change date",
}}
keyboardIcon={<Icon icon={ICONS.Cool_icon} />}
className={classes.componentStyle} // do not overide , but puts on top
/>
makeStyles is a hook factory that returns a style hook (usually called useStyles), this is how it's used:
const useStyles = makeStyles(...);
In your code, you define useStyles as a function that return makeStyles instead of telling makeStyles to create a new hook which doesn't make sense here, so change your code to the above. I also fixed the styles for you. The text color styles should be placed in InputBase component:
const useStyles = makeStyles(() =>
createStyles({
componentStyle: {
verticalAlign: "middle",
fontSize: "12px",
width: (params) => (params.width ? params.width : "auto"),
"& fieldset": {
border: "solid 2px #0070D8"
},
"& .MuiInputBase-root": {
height: (params) => (params.height ? params.height : "auto"),
color: (params) => (params.color ? params.color : "inherit")
}
}
})
);
const classes = useStyles({
color: "red",
width: 400,
height: 80,
});
<KeyboardDatePicker
onChange={() => {}}
inputVariant="outlined"
InputProps={{
className: classes.componentStyle
}}
/>
If you want to style via createMuiTheme, here is the equivalent code. Note that you can't pass the component props to create dynamic styles unlike the useStyles approach above:
const theme = createMuiTheme({
overrides: {
MuiTextField: {
root: {
verticalAlign: "middle",
fontSize: "12px",
width: 150,
"& fieldset": {
border: "solid 2px #0070D8"
}
}
}
}
});
And it should work again. For reference, see this section to know how you can use makeStyles with component props.
It seems you don't need to write a custom hook like this useStyles = (params: any) => ..., the hook returned by makeStyles already accepts a props param.
When styling MUI components you need to check the API for each component to define the object you pass to makeStyles, in this case, the date picker component is a group of other MUI components, if you go to the API you'll see different props to pass to each individual component. To style the input you pass the classes returned by the useStyle hook in InputProps, with root rule as it is in the Input API, apply other rules if you need more specific styles.
const useInputStyles = makeStyles({
root: {
width: (props) => (props.width ? props.width : "auto"),
color: (props) => (props.color ? props.color : "inherit"),
verticalAlign: "middle",
fontSize: "12px",
border: "solid 2px #0070D8"
}
});
...
const inputClasses = useInputStyles()
...
<KeyboardDatePicker
...
InputProps={{ classes: inputClasses }}
/>
and to style the "board", not sure if you mean the popover, since you use the inline variant, you pass the styles in the PopoverProps, defining the styles in the paper rule as described in the Popover API
const usePopoverStyles = makeStyles({
paper: {
backgroundColor: "green"
}
});
...
const popoverClasses = usePopoverStyles();
...
<KeyboardDatePicker
...
PopoverProps={{ classes: popoverClasses }}
/>
you can see it working here https://codesandbox.io/s/mui-keyboarddatepicker-styles-sueqd?file=/src/App.tsx
I have implemented it like this in TS, not a finished component, but I hope that this assists people. I am about to add MuiFormLabel-root etc to add more specific styling to the label.
const useDatePickerStyles = makeStyles<ITheme, ITextFieldStyleProps>((theme) =>
createStyles({
datePickerContainer: ({ isValid, isError }) => ({
border: 'solid',
borderRadius: 4,
borderWidth: theme.mvf.border.width.thin,
borderColor: theme.mvf.palette.border,
...(!isError && {
'&:hover': {
boxShadow: theme.mvf.boxShadow.primary,
borderColor: theme.mvf.palette.primary.main,
},
...(isValid && {
color: theme.mvf.palette.primary.main,
boxShadow: theme.mvf.boxShadow.primary,
borderColor: theme.mvf.palette.primary.main,
}),
}),
...(isError && {
color: theme.mvf.palette.error,
boxShadow: theme.mvf.boxShadow.error,
borderColor: theme.mvf.palette.error,
}),
}),
datePicker: () => ({
margin: theme.mvf.spacing.small,
}),
}),
);
export default useDatePickerStyles;
And get access to classes like so
const DatePicker: DatePickerType = ({
id,
onChange,
format,
value,
label,
errorMessage,
placeholder,
isVerticallyCentered,
...props
}: IDatePickerProps) => {
const isValid = !errorMessage && !!value;
const classes = useDatePickerStyles({
isError: !!errorMessage,
isVerticallyCentered,
isValid,
});
return (
<div className={classes.datePickerContainer}>
<MuiPickersUtilsProvider utils={DateFnsUtils}>
<KeyboardDatePicker
id={id}
fullWidth
maxDateMessage={''}
minDateMessage={''}
invalidDateMessage={''}
className={classes.datePicker}
label={isVerticallyCentered ? undefined : label} // don't show as label will be outside
placeholder={placeholder}
format={format} // of the displayed date
emptyLabel={placeholder} // displayed value if empty
name="datePicker"
InputLabelProps={{
className: classes.inputLabel,
}}
margin="normal"
value={value}
onChange={onChange}
InputProps={{
className: classes.inputPropsClasses,
inputProps: { className: classes.textInput },
disableUnderline: true,
}}
inputVariant="standard"
KeyboardButtonProps={{
className: classes.calendarButton,
}}
{...props}
/>
</MuiPickersUtilsProvider>
</div>
);
};

Change Material-UI outlined Chip focus and hover color

Trying to add styles to a Material-UI chip (outlined variant) upon hovering, but not getting the expected results.
The border color is white, but the background color doesn't change at all.
So I'm questioning whether backgroundColor is even the right property anymore, but what else can it be?
const CustomChip = withStyles(theme => ({
root: {
"&:hover": {
borderColor: "white",
backgroundColor: "green"
}
}
}))(Chip);
Below are the default background-color styles for the outlined variant of Chip:
/* Styles applied to the root element if `variant="outlined"`. */
outlined: {
backgroundColor: 'transparent',
'$clickable&:hover, $clickable&:focus, $deletable&:focus': {
backgroundColor: fade(theme.palette.text.primary, theme.palette.action.hoverOpacity),
},
In the styles above, $clickable& will be resolved to .MuiChip-clickable.MuiChip-outlined. The important aspect being that this rule is specified using two class names in addition to the pseudo-class (:hover or :focus). This means that these default styles will have greater specificity than the style rule you used for your override (which only uses one class name plus the pseudo-class). In order for your override to be successful, it needs to have specificity equal to or greater than the default styles.
One simple way to do this is to double the &. This causes the generated class name (which the ampersand refers to) to be specified twice in the rule -- increasing its specificity to match the default styles.
Here's a working example:
import React from "react";
import { makeStyles, withStyles } from "#material-ui/core/styles";
import Avatar from "#material-ui/core/Avatar";
import Chip from "#material-ui/core/Chip";
const useStyles = makeStyles((theme) => ({
root: {
display: "flex",
justifyContent: "center",
flexWrap: "wrap",
"& > *": {
margin: theme.spacing(0.5)
}
}
}));
const StyledChip = withStyles({
root: {
"&&:hover": {
backgroundColor: "purple"
},
"&&:focus": {
backgroundColor: "green"
}
}
})(Chip);
export default function SmallChips() {
const classes = useStyles();
const handleClick = () => {
console.info("You clicked the Chip.");
};
return (
<div className={classes.root}>
<StyledChip variant="outlined" size="small" label="Basic" />
<StyledChip
size="small"
variant="outlined"
avatar={<Avatar>M</Avatar>}
label="Clickable"
onClick={handleClick}
/>
</div>
);
}

Reddit text field implementation Material-UI

So I'm trying to immitate the reddit text field implementation from material-ui, I've gone ahead and setup this custom component, but I'm getting a invalid hook call error everytime I run on the const classes=... Line
Here's the code:
import React, { Component } from "react";
import { TextField } from "#material-ui/core";
import { fade, makeStyles } from "#material-ui/core/styles";
import styles from "./LNTextField.module.css";
const useStylesReddit = makeStyles(theme => ({
root: {
border: "1px solid #e2e2e1",
overflow: "hidden",
borderRadius: 4,
backgroundColor: "#fcfcfb",
transition: theme.transitions.create(["border-color", "box-shadow"]),
"&:hover": {
backgroundColor: "#fff"
},
"&$focused": {
backgroundColor: "#fff",
boxShadow: `${fade(theme.palette.primary.main, 0.25)} 0 0 0 2px`,
borderColor: theme.palette.primary.main
}
},
focused: {}
}));
class LNTextField extends Component {
render() {
var classNames = require("classnames");
const classes = useStylesReddit();
return (
<TextField
InputProps={{ classes, disableUnderline: true }}
{...this.props}
/>
);
}
}
export default LNTextField;
Also since I just copied it I'm not sure how I can type this code in a seperate css files and refer to the hover and focused bits appropriately, so If you could also tell me how to do that that'd be great. Thanks!
According to React, you are getting this error because:
You can’t use Hooks inside of a class component
Convert your class component to functional component:
const LNTextField = props => {
var classNames = require("classnames");
const classes = useStylesReddit();
return (
<TextField
InputProps={{ classes, disableUnderline: true }}
{...props}
/>
);
}

React makeStyles doesn't set background image

Despite trying several ways to load the image for the backgroundImage property, it never shows up in page. Loading external images (for example from google) works as expected.
I tried:
backgroundImage: `url(${Papyrus})`
backgroundImage: "url(" + Papyrus + ")"
backgroundImage: "url(../../assets/images/papyrus.png)"
backgroundImage: Papyrus
backgroundImage: "url(\"../../assets/images/papyrus.png\")"
backgroundImage: "url(assets/images/papyrus.png)"
NONE of them work. The image is loaded when I look at my network audit, I can find it in the static folder, but it's never displayed.
App.tsx
import React from 'react';
import makeStyles from './app-styles';
import {Container} from "#material-ui/core";
import Description from "../description/description";
const App: React.FC = () => {
const classes = makeStyles();
return (
<div className="App">
<Container maxWidth={"xl"}>
<div className={classes.row}>
<Description/>
</div>
</Container>
</div>
);
};
export default App;
description.tsx
import * as React from "react";
import makeStyles from './description-styles';
interface DescriptionProps {
}
const Description: React.FC<DescriptionProps> = () => {
const classes = makeStyles();
return (
<div className={classes.descriptionCard}>
<p>Some text</p>
</div>
)
};
export default Description;
description-styles.tsx
import makeStyles from "#material-ui/core/styles/makeStyles";
import Papyrus from "../../assets/images/papyrus.png";
export default makeStyles(theme => ({
descriptionCard: {
backgroundImage: `url(${Papyrus})`,
// margin: 'auto',
height: '25vh',
width: 'calc(20vw * 0.54 - 2%)',
borderRadius: 8,
display: 'flex',
marginLeft: '10px',
marginTop: '10px'
},
text: {
}
}))
Add some additional properties to the background image and it will work -
descriptionCard: {
backgroundImage: `url(${Papyrus})`,
backgroundPosition: 'center',
backgroundSize: 'cover',
backgroundRepeat: 'no-repeat',
// margin: 'auto',
height: '25vh',
width: 'calc(20vw * 0.54 - 2%)',
borderRadius: 8,
display: 'flex',
marginLeft: '10px',
marginTop: '10px'
}
I'm not sure why we need these additional properties (maybe someone could add to the answer), but sometimes the image needs certain behaviour to be defined, like size, position, etc.
You should write it line this:
backgroundImage: `url(images/papyrus.png)`
And it should work.
This way works for me
import LaptopImage from "../../assets/laptop.jpg";
...
const useStyle = makeStyles((theme) => ({
wrapper:{
backgroundImage: `url(${LaptopImage})`,
height: '100vh'
}
})
Its the bare minimum. Rest you can align it properly.
use props, try this:
const useStyles = makeStyles({
bg: props => ({
backgroundImage: \`url(${props.backgroundImage})\`
})
})
In React, you can import a picture first, after that use it as a component.
import yourPicture from './assets/img/yourPicture.png'
...
const userStyles = makeStyles({
root: {
backgroundImage: `url(${yourPicture})`,
minHeight: '100vh', // set height size 100%
},
})
I've been facing this problem all morning. Here is how I fixed. First, import the image then add it to the string:
import banner_background from "./banner_background.png";
backgroundImage: `url(${banner_background})`

How to change the default properties of a css framework as material ui

I'm pretty new to css and i'm a little confused here. I'm using material ui with react and redux. I want somehow to edit some properties of a specific component. For example suppose we use TextField with disabled property. As i can see the disabled property contains these properties(i saw that from the material ui node modules in textfield).
var styles = {
root: {
borderTop: 'none',
borderLeft: 'none',
borderRight: 'none',
borderBottomStyle: 'solid',
borderBottomWidth: 1,
borderColor: borderColor,
bottom: 8,
boxSizing: 'content-box',
margin: 0,
position: 'absolute',
width: '100%'
},
disabled: {
borderBottomStyle: 'dotted',
borderBottomWidth: 2,
borderColor: disabledTextColor
},
But i dont want when it's disable for the borderBottomLine to be dotted. I want to change it to hidden. How to do such an action without affecting the frameworks code?
You can override some default styles of material-ui components. Look at this section of docs. Pay attention to this example:
import React from 'react';
import {cyan500} from 'material-ui/styles/colors';
import MuiThemeProvider from 'material-ui/styles/MuiThemeProvider';
import getMuiTheme from 'material-ui/styles/getMuiTheme';
import AppBar from 'material-ui/AppBar';
// This replaces the textColor value on the palette
// and then update the keys for each component that depends on it.
// More on Colors: http://www.material-ui.com/#/customization/colors
const muiTheme = getMuiTheme({
textField: {
backgroundColor: 'yellow',
},
datePicker: {
color: 'yellow',
},
});
// MuiThemeProvider takes the theme as a property and passed it down the hierarchy.
const Main = () => (
<MuiThemeProvider muiTheme={muiTheme}>
<AppBar title="My AppBar" />
</MuiThemeProvider>
);
export default Main;
Here, we override background-color for TextField component and color for DatePicker. You should import getMuiTheme function, pass to its object with properties which you want to override. Unfortunately, for disabled TextField you can override only text color. You can check all properties which you can override from source of default theme - https://github.com/callemall/material-ui/blob/master/src/styles/getMuiTheme.js
const muiTheme = getMuiTheme({
textField: {
backgroundColor: 'yellow',
},
datePicker: {
color: 'yellow',
},
});
After that, you should pass muiTheme to the eponymous property
of MuiThemeProvider component. This component should wrap root-component of your application.
const Main = () => (
<MuiThemeProvider muiTheme={muiTheme}>
<AppBar title="My AppBar" />
</MuiThemeProvider>
);
Here's sample code. Use style in your preferred jsx tag and edit it normally like CSS, but the properties & values must be inside quotation marks("").
import React from "react";
import AppBar from "#mui/material/AppBar";
import Toolbar from "#mui/material/Toolbar";
const index = () => {
return (
<AppBar style={{ backgroundColor: "black", height: "65px" }}>
<Toolbar></Toolbar>
</AppBar>
);
};
export default index;

Resources