0
votes

I'm having some trouble using styled-components in a React app (created with create-react-app) where I also use material-ui.

I'm a noobie on styled-components so I was trying to style a material-ui component that is inside a styled-component based on another material-ui component. To clarify what i was trying to do, here is the code:

const StyledContainer = styled(Container)`          
    background-color: ${props=>props.theme.defaultBackground};
    ${FormControl} {
        width:100%;
      }
`;

Where Container and FormControl are indeed material-ui components.

Now I know I'm not supposed to style children in the parents, but as I said, I'm just practicing.

When I do that, and use StyleContainer I get a PropType error:

Calling PropTypes validators directly is not supported by the `prop-types` package. Use `PropTypes.checkPropTypes()` to call them. Read more at ...

with this being the stack trace:

checkType
node_modules/prop-types/factoryWithTypeCheckers.js:181
flatten
http://localhost:3000/static/js/0.chunk.js:226001:21
ComponentStyle.generateAndInjectStyles
http://localhost:3000/static/js/0.chunk.js:226243:27
useInjectedStyle
http://localhost:3000/static/js/0.chunk.js:226460:120
useStyledComponentImpl
http://localhost:3000/static/js/0.chunk.js:226488:28
Styled(WithStyles(ForwardRef(Container)))
http://localhost:3000/static/js/0.chunk.js:226555:12
renderWithHooks
node_modules/react-dom/cjs/react-dom.development.js:14803
updateForwardRef
node_modules/react-dom/cjs/react-dom.development.js:16816
beginWork
node_modules/react-dom/cjs/react-dom.development.js:18645
HTMLUnknownElement.callCallback
node_modules/react-dom/cjs/react-dom.development.js:188
invokeGuardedCallbackDev
node_modules/react-dom/cjs/react-dom.development.js:237
invokeGuardedCallback
node_modules/react-dom/cjs/react-dom.development.js:292
beginWork$1
node_modules/react-dom/cjs/react-dom.development.js:23203
performUnitOfWork
node_modules/react-dom/cjs/react-dom.development.js:22154
workLoopSync
node_modules/react-dom/cjs/react-dom.development.js:22130
performSyncWorkOnRoot
node_modules/react-dom/cjs/react-dom.development.js:21756
scheduleUpdateOnFiber
node_modules/react-dom/cjs/react-dom.development.js:21188
updateContainer
node_modules/react-dom/cjs/react-dom.development.js:24373
(anonymous function)
node_modules/react-dom/cjs/react-dom.development.js:24758
unbatchedUpdates
node_modules/react-dom/cjs/react-dom.development.js:21903
legacyRenderSubtreeIntoContainer
node_modules/react-dom/cjs/react-dom.development.js:24757
render
node_modules/react-dom/cjs/react-dom.development.js:24840

Can you help me to figure this out!

Thanks!

1

1 Answers

2
votes

You can only refer to components inside another if the referred one is a styled component. From the docs:

This behaviour is only supported within the context of Styled Components: attempting to mount B in the following example will fail because component A is an instance of React.Component not a Styled Component.

The error thrown - Cannot call a class as a function - occurs because the styled component is attempting to call the component as an interpolation function.

However, wrapping A in a styled() factory makes it eligible for interpolation -- just make sure the wrapped component passes along className.

That is:

const StyledFormControl = styled(FormControl);

const StyledContainer = styled(Container)`          
    background-color: ${props=>props.theme.defaultBackground};
    ${StyledFormControl} {
      width:100%;
    }
`;