Search code examples
reactjsstyled-componentstailwind-cssemotion

Props, TailwindCSS & Twin.Macro


I am trying to get the following component to work properly with Twin.Macro:

import "twin.macro";

const Pattern = ({ classes }) => {
  return (
    <div css={[classes.wrapper]}>
      <img
        src="..."
        css={[classes.img]}
      />
    </div>
  );
};

In other words, I would like to receive the props via the classes prop and pass the values on to Twin.Macro. However, it is not working properly. For example, here is an implementation of that component:

<Pattern
  classes={{
    wrapper: "absolute -left-2 z-10 lg:left-0 top-0 h-full bg-contain bg-line-left-md lg:bg-line-left bg-no-repeat xl:bg-line-left-md hidden sm:block",
    img: "h-full",
  }}
/>

And here is the css that is output:

.css-w36jn9-Pattern {
    absolute -left-2 z-10 lg: left-0 top-0 h-full bg-contain bg-line-left-md lg:bg-line-left bg-no-repeat xl:bg-line-left-md hidden sm:block;
}

As you can see, all it does is pass on the values of the tailwind css classes. It does not process those classes in the proper property-value pairs (such as position: absolute; left: -2px, etc).

I have tried different ways to get this to work, but nothing has been successful. Any idea what I am doing wrong and how to fix it?

Thanks.


Solution

  • accordingly to Twin.Macro when passing css property, you need to pass your classes to tw function using tagged template literals. given you are passing a variable use also string interpolation.

    finally, your code should look like:

    import tw from "twin.macro";
    
    const Pattern = ({ classes }) => {
      return (
        <div css={[tw`${classes.wrapper}`]}>
          <img
            src="..."
            css={[tw`${classes.img}`]}
          />
        </div>
      );
    };