Override a Material UI style without using an HOC? - css

Is there any way to override a Material UI components styling without having to create a whole new component using withStyles()?
For instance, say I am rendering the following and I just want to change the color of the "Delete" label:
<div style={styles.rowFooter}>
<FormControlLabel
control={<ClearIcon />}
label="Clear"
title="Clear all fields."
onClick={clearFields}
/>
<FormControlLabel
control={<DeleteIcon />}
label="Delete"
title="Delete this row."
onClick={deleteRow}
/>
</div>
To do this, I'd usually have to:
Create a new styles function that returns { color: "maroon" }.
Create a new component to render the "Delete" button.
Wrap my new component withStyles(newStylesFn)(MyComponent).
But I don't want to do all of that. Is there any way to avoid it?
Update:
One way that I know of is to just pass a CSS className. I was looking for something besides that because it doesn't even work in this situation to override the nested element.
What I'd really like to be able to do is just pass style={{ color: "maroon" }}, but that only changes the color of the icon, not the actual label text...

You could use the classes prop to override styles provided by Material UI instead of className.
<FormControlLabel
control={<DeleteIcon />}
label="Delete"
title="Delete this row."
classes={{
label: 'labelStyle'
}}
/>
styles.css
.labelStyle {
color: maroon !important;
}
Although it's Not the perfect solution, it still does the job without using withStyles().

Related

Styling Material UI components using CSS

I have a Material UI component, and I am trying to custom style it using the CSS.
Following is the code:
<IconButton className="my-class">
<Close />
</IconButton>
CSS:
.my-class {
float: right;
margin-left: auto;
margin-right: 0;
}
But I am not able to style it, when I tried the following, it works:
<IconButton style={{ float: 'right', marginLeft: 'auto', marginRight: '0' }}>
<Close />
</IconButton>
Why I am not able to style the Material UI components using regular CSS?
Most CSS-in-JS solutions inject their styles at the bottom of the HTML <head>, which gives MUI precedence over your custom styles.
You need to use the StyledEngineProvider exported from #mui/material/styles with the injectFirst option, in order for the CSS injection order to be correct. It is explained here.
So something like this shoud work:
<StyledEngineProvider injectFirst>
<IconButton className="my-class">
<CloseIcon></CloseIcon>
</IconButton>
</StyledEngineProvider>
You can style MUI components using several ways like GlobalStyles API, sx, styled or even normal way.
If you are going to style the particular component like IconButton, and if you have a look at the document for the API, you can find the class names for the component.
Here's couple of references.
https://mui.com/customization/how-to-customize/#main-content
How to give conditional style to MUI TextField?

Nested Menu Item in React

I have a problem in displaying the values from the TextField in my React app.
I'm using material UI and material-ui-phone-number as its packages. As you can see, the values after i click the flag, it is displaying on the back. I believe this is on the zIndex. Pls modify only the dialog2.js
Pls check my codesandbox here
CLICK HERE
Your MuiPhoneNumber utilizes a MUI modal for the country selection & its default z-index is 1300. It does not look like they expose a prop to alter its css properties so you can just target #country-menu (the id of the modal) using any preferred styling solutions
<div>
<style type="text/css">
{`
#country-menu {
z-index: 1801;
}
`}
</style>
<DialogContent style={{ width: 300, height: 500 }}>
<MuiPhoneNumber
name="MobileNo"
label="Mobile No."
variant="outlined"
fullWidth
defaultCountry={"vn"}
value={selectedValue}
onChange={(e) => setSelectedValue(e)}
/>
</DialogContent>
</div>
This can be achieved by doing the following changes:
Remove all CSS z-index defined
Put the Dialog 2 in Dialog 1 content
Here is the working CSB Link: https://codesandbox.io/s/nested-dialog-menuitem-dropdown-forked-wymm0?file=/dialog1.js

Material-ui style dialog / modal backdrop

How do I go about styling the transparent dark overlay of a material-ui dialog or modal?
I'm using material-ui/React/Typescript.
Instead of a transparent dark, I want it to be a transparent white.
I'd prefer a JSS solution but an inline style is welcomed.
You can use the BackdropProps property of the modal:
<Modal
aria-labelledby="simple-modal-title"
aria-describedby="simple-modal-description"
open={this.state.open}
onClose={this.handleClose}
BackdropProps= {{
classes: {
root: classes.backDrop
}
}}
>
and in your style object:
...
backDrop: {
background: 'rgba(255,255,255,0.2)',
},
The API for this has changed a bit in the last couple of years. BackdropProps is now referenced by slotProps.backdrop. Meaning the component now takes a slotProps prop, that receives an object, one of the properties being backdrop all lowercase. backdrop takes an object that can include many things, including a style prop that you use like usual.
<Modal
slotProps={{ backdrop: { style: { backgroundColor: 'rgba(255,255,255,0.2)' } } }}
>
</Modal>

Make an unclickable Menu Item

I'm doing a Dropdown menu using Ant Design:
import React, { Component } from "react";
import { Icon, Dropdown, Menu } from "antd";
const { Item } = Menu;
class NotificationBell extends Component {
render() {
const menu = (
<Menu>
<Item><p>You must be connected to get notifications.</p></Item>
</Menu>
);
return (
<Dropdown overlay={menu} trigger={['click']}>
<Icon type="bell" theme="outlined" />
</Dropdown>
);
}
}
Ant this is what I get:
But I don't want to just remove the highlight, I also want to make the component unclickable, i.e. instead of a "hand cursor" I want a "normal cursor".
Adding the selectable={false} prop on the Menu component as suggested by the Ant Design documentation doesn't help. What should I do?
Thank you for your help.
The documentation you linked to specifies a disabled prop on Menu.Item which may or may do what you want. If you want to do something other than what the library provides, you can customize the behavior.
You can use the CSS property cursor to specify which cursor you want on hover.
You might want to use not-allowed for a disabled-style cursor, or the default arrow: default.
Docs
For future reference, you can't prevent a user from clicking on the element. What you want to do is actually to communicate the affordance (or lack thereof) using visual cues, and potentially alter the behavior of your application when receiving that input.
The CSS property pointer-events set to none makes the component ignore mouse events without altering the style of the cursor.
<Menu>
<Menu.Item key="/">
<Link href="/">Clickable</Link>
</Menu.Item>
<Menu.Item style={{ pointerEvents: 'none' }}>
Unclickable
</Menu.Item>
</Menu>here

Change styling on hover semantic-ui-react components

if I set up a className for certain components like
<Segment className="Change" color='blue' inverted></Segment>
and in my css I use
.Change:hover{
background-color: black; //or any other change on hover
}
nothing is overriden on the hover.
I have also noticed there are many other components that refuse changes of mine, seemingly randomly. One semantic component will let me change a width the next will not. Is the cause from the same issue? How do I override the color on a hover?
After reviewing the source code of Segment Component (github), I found it has two default classes: segment and ui. In addition, you used two props color=blue and inverted. So I would recommend using the following code.
.ui.segment.blue.inverted.Change:hover {
background-color: black !important;
}
Working DEMO
Choose any color semantic-ui provide for example:
<Form>
<Form.Input label="Email" type="email" />
<Form.Input label="Password" type="password" />
<Button color="teal" type="submit">
Sign In
</Button>
</Form>
Your button appears like:
You can add inverted props inside Button component that react semantic-ui provide
<Form>
<Form.Input label="Email" type="email" />
<Form.Input label="Password" type="password" />
<Button inverted color="teal" type="submit">
Sign In
</Button>
</Form>
your component appears like:
On hover returns to basic style opposite of inverted
styled components usage with react semantic ui
I recommended you to use styled-components in order to override semantic-ui component style
import { Tab, Form, Button, Grid, Icon } from "semantic-ui-react";
import styled from "styled-components";
const Mybutton = styled(Button)`
&:hover {
color: #fff !important;
}
`;
Next use your new styled component instead of semantic-ui
<Mybutton inverted color="teal" type="submit">
Sign In
</Mybutton>
Because you didn't provide more code, hard to guess what overriding style you try to change. Try to add !importanant rule to this style.
.Change:hover {
background-color: black !importanant;
}
To avoid !important, which is not always a good solution, add a more specific CSS selector, for exaple Segment.Change:hover.
UPDATE:
Try to remove color='blue' from the template and check if will work with and without !important rule.

Resources