1

I am trying to animate some things using Motion (previously Framer Motion) for React (19) in a NextJS 15 project.

The problem is, that I cannot apply the colors defined in the global.css file in different variables to the motion.div component.

Here is the code snippet I am working with

import React from 'react';

import { motion } from 'motion/react';

type Props = {
    target: string;
    title: string;
};

const NavLink = (props: Props) => {
    return (
        <motion.div
            layout
            className="mt-1 cursor-pointer uppercase text-xs mx-2 relative"
            initial={{ color: `var(--muted)` }} // <---- Not Applying
            whileHover={{ color: ['var(--muted)', 'var(--primary)'] }} // <---- Not Working
            transition={{ duration: 0.2 }}
            onClick={() => console.log(props.target)}
        >
            {props.title}
        </motion.div>
    );
};

export default NavLink;

The Tailwindcss classes are not changing either, so instead if I try to do className: 'text-muted' does not work in motion, otherwise it does.

Not sure what the issue is, I am relatively new to NextJS and first time using Framer motion, so I'm probably not doing something obvious.

1 Answer 1

1

Is your global.css created with shadcn/ui? If so, note that the global.css file looks something like this:

@layer base {
  :root {
    --background: 0 0% 100%;
    --foreground: 0 0% 3.9%;
   }
}

and the rules looks like hsl(var(--primary)) (as the css variables are HSL values), so something like initial={{ color: 'hsl(var(--muted))' }} should display the correct color.

However, motion transition does not seems to work with this kind of wrapping (they can change color but not the animation), and the css variables should be color directly (something like #ffffff or hsla(244 100% 50%)) for it to work correctly.

Below is a working example:

/* global.css */
@layer base {
  :root {
    --primary: hsl(244 100% 50%);
    --muted: hsl(321 100% 50%);
  }
}
/* ... */
"use client"; //motion probably need use client to work
import React from "react";

import { motion } from "motion/react";

type Props = {
  target: string;
  title: string;
};

const NavLink = (props: Props) => {
  return (
    <motion.div
      layout
      className="mt-1 cursor-pointer uppercase text-xs mx-2 relative"
      initial={{ color: `var(--muted))` }}
      whileHover={{
        color: "var(--primary)",
        transition: { duration: 0.5 },
      }}
      onClick={() => console.log(props.target)}
    >
      {props.title}
    </motion.div>
  );
};

export { NavLink };

As a side note, if you are using tailwind anyway, it may be a good idea to just use the transition of tailwind.

Sign up to request clarification or add additional context in comments.

1 Comment

Yeah, I ended up using the tailwind transition itself, but I will try to update the CSS variables as you have mentioned. Thanks for the help!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.