custom props doesn't work in material-ui components - reactjs

i want to add ( background & color ) custom props, to the mui button, like this:
<ButtonCustom bg="#6415ff" color="#f7fafc">Sign Up</ButtonCustom>
<ButtonCustom bg="#e2e8f0" color="#4a5568">Search</ButtonCustom>
file: ButtonCustom.js
import Button from "#mui/material/Button";
import { styled } from "#mui/system";
const ButtonStyled = styled(Button)`
background-color: ${({ bg }) => bg};
color: ${({ color }) => color};
padding: 16px 0;
&:hover {
background-color: #5011cc;
}
font-size: 16px;
width: 12rem;
`;
export default ButtonStyled;
But it will give me this error:
TypeError
Cannot read properties of undefined (reading 'main')
so my question is : how can i add more than one custom props??
Thank you very much for giving me time and answering this question.

Related

How to make #emotion/style styles change when a class is changed on a div

SandBox: https://codesandbox.io/s/infallible-nash-x91zz?file=/src/App.js
In the sandbox I have an emotion style defined. It has two classes it in — open and closed.
I am using a state to toggle the classes and the classes are toggling correctly according to the inspector.
Problem: styles not updating on state change.
Expected behavior: background color on div will change when class changes between open and closed
Actual Behavior: The classes are being updated but the stiles are not.
Code:
import React, { useState } from "react";
import "./styles.css";
import styled from "#emotion/styled";
const MenuContainer = styled.div`
.open {
background-color: blue;
width: 600px;
height: 600px;
}
.closed {
background-color: red;
width: 600px;
height: 600px;
}
`;
export default function App() {
const [openState, setOpenState] = useState(false);
return (
<MenuContainer className={openState ? "closed" : "open"}>
<button value="click" onClick={() => setOpenState(!openState)}>
Click Me
</button>
</MenuContainer>
);
}
You should do this:
const MenuContainer = styled.div`
width: 600px;
height: 600px;
&.open {
background-color: blue;
}
&.closed {
background-color: red;
}
`;

How can I get variables from my Theme with styled components and use within astroturf css

I've come across a "problem" which is making me feel like I've chosen the wrong stack for what I'd like. I'm pretty new with React & Typescript but I wondered if anyone knew of a way too do the following.
theme.ts
import { createGlobalStyle } from "styled-components"
import { ThemeType } from "../types/theme"
export const lightTheme = {
background: "#F2F3EF",
text: "#252524",
}
export const darkTheme = {
background: "#1C282B",
text: "#F2F3EF",
}
export const GlobalStyles = createGlobalStyle<{ theme: ThemeType }>`
body {
margin: 0;
margin-left: 300px;
background: ${({ theme }) => theme.background};
color: ${({ theme }) => theme.text};
font-family: Tahoma, Helvetica, Arial, Roboto, sans-serif;
}
`
styles.ts
import { css } from "astroturf"
import { useTheme } from "styled-components"
const theme = useTheme()
const styles = css`
.navContainer {
width: 300px;
height: 100%;
position: absolute;
top: 0;
left: 0;
}
.themeToggle {
position: absolute;
bottom: 0;
text-align: left;
padding: 15px;
}
.logo {
padding: 20px;
}
.menuItems {
a {
text-decoration: none;
display: block;
padding: 5px;
}
a.light:hover {
background-color: ${({ theme }) => theme.background};
}
a.dark:hover {
background-color: ${({ theme }) => theme.background};
}
}
`
export default styles
I get the following error message, which DOES make sense
Could not resolve interpolation to a value, css returned class name,
or styled component. All interpolated styled components
must be in the same file and values must be statically determinable at
compile time
I'm running webpack with postcss but also, trying to use themes from style-components.
The end goal is to use a toggle switch to change theme from light/dark but I just need some guidance on what approach I should be taking. Clearly implementing css-in-js with astroturf for postcss is going to be problematic with the way I've used themes but I wanted to ask you guys before I tear it out.
There could be an easy solution which I'm missing. I have tried just importing the variables light and dark and then trying to use those within my css string but, this also doesnt work.
Thanks in advance

Extend a Styled Component from a different file

What I'm trying to achieve is to be able to add extra styling to my Button.tsx(essentially extending the styles) when using this component in different files. As you can see in my Button.tsx I have defined some default styles I would like the button to have, but as I use more buttons across my app, I might want to change the background or color, etc.
One thing I could do is this:
Example of not what I want to do:
import React from 'react'
import styled from 'styled-components'
interface IButton = {
children: string
}
export default function Button({ children }: IButton) {
const Button = styled.button`
padding: 1em;
background: #ccc;
border-radius: 5px;
`
const RedButton = styled(Button)`
// Inherits all of the styles from Button.
background: red;
`
return (
<Button>{children}</Button
)
}
This example will inherit my Button styles and then allows me to extend. The problem with this solution is, if I decide to add more buttons, I will always have to come back to this file and then add the different variants, which could start to make this file get pretty chunky and messy.
Ideally I would like to extend my <Button> from the App.tsx file, or which ever file I'm using my <Button> in.
How could I adjust the code below to achieve this?
Button.tsx
import React from 'react'
import styled from 'styled-components'
interface IButton = {
children: string
}
export default function Button({ children }: IButton) {
const Button = styled.button`
padding: 1em;
background: #ccc;
border-radius: 5px;
`
return (
<Button>{children}</Button
)
}
App.tsx
import React from 'react'
import styled from 'styled-components'
export default function App() {
return (
{/* This button would render with the default styles from Button.tsx */}
<Button>Button One</Button>
{/* This button would render with extended styles, a blue background for example */}
<Button>Button Two</Button>
)
}
In your App.tsx you can do the same:
const BlueButton = styled(Button)`
background: blue;
`
what styled-components does is it creates a class with background blue and pass it to your Button. so in your Button.tsx you need to accept the css class
export default function Button({ className, children }: IButton) {
const Button = styled.button`
padding: 1em;
background: #ccc;
border-radius: 5px;
`
return (
<Button className={className}>{children}</Button
)
}
Edit
another way to do is to export the style like this
const BaseStyles = css`
padding: 1em;
background: #ccc;
border-radius: 5px;
`
const BaseButton = styled.button`
${BaseStyles}
`
Then later override the styles
const BlueButton = styled.button`
${BaseStyles}
background: blue;
`

Passing a custom class/style to a styled-component in Gatsby (React)

I've created the following styled-component for my gatsby project.
import React from "react"
import styled, { css } from 'styled-components'
const Button = styled.div`
background-color: #4E58F5;
width: 200px;
padding: 20px;
margin-right: 30px;
margin-top: 30px;
border-radius: 30px;
color: #FFFFFF;
transition: background-color 0.25s ease;
${props => props.primary && css`
background-color: #FFF;
color: red;
`}
`;
export default props => (
<Button>{props.buttonText}</Button>
)
I've not found the examples in the documentation to be clear or consistent enough to understand how I should be passing in the "primary" option to my components.
I'm trying to do the following, on my index.js page. The Button renders, but the primary word has no effect. What am I missing here?
<Button primary buttonText="Submit" />
The component you're exporting, does not recognize the primary property, and thus cannot pass it on to the Button element. You can fix this either by exporting the styled component itself, or by passing unrecognized props to the Button.
const Button = styled.div`
[...]
`;
export default Button;
OR
export default ({buttonText, ...props})=>(
<Button {...props}>{buttonText}</Button>
);

Invariant Violation: "borderLeft" is not a valid style property

I'm using styled-components in a React Native project and I'm trying to set a left border in a text component.
import React, { Component } from 'react';
import styled from 'styled-components';
const TitleText = (props) => {
return (
<Text>{props.text}</Text>
);
};
const Text = styled.Text`
font-family: ${props => props.theme.fontFamily};
color: ${props => props.theme.darkBlue};
border-left: 1px solid #000;
`;
The problem is that after adding border-left: 1px solid #000and reload the app, it shows: "Invariant Violation: "borderLeft" is not a valid style property".
How can I add a left border to that component using styled components?
I don't believe it's possible to directly set the border left (or top, right, bottom) style property on components in react native.
This is likely to be the cause of your error, in that there is no mapping from border-left to any equivalent styling property in react native.
Your best best might be to explicitly specify the border property values per side as follows:
const Text = styled.Text`
font-family: ${props => props.theme.fontFamily};
color: ${props => props.theme.darkBlue};
/* Note that react native typically requires the same
border style to be applied to all sides of a component
that supports borders */
border-style: solid;
/* Most components in react native support unique border width and
colors on each side of the component */
border-left-color: #000;
border-left-width: 1px;
`;
Following changes should solve the issue-
import React, { Component } from 'react';
import styled from 'styled-components';
const TitleText = (props) => {
return (
<Text>{props.text}</Text>
);
};
const Text = styled.Text`
font-family: ${props => props.theme.fontFamily};
color: ${props => props.theme.darkBlue};
border-left-width: 1px;
border-left-style : solid;
border-left-color : #fff
`;
Refer following links for available properties -
Layout Props
StyleSheetGuide

Resources