I would like to control when an animation (Framer Motion) can run using window.innerWidth
, but in Next.js I get the following error message:
ReferenceError: window is not defined
This is a simplified version of my component named ValuesSection.jsx:
import React, { useEffect } from "react";
import { useInView } from "react-intersection-observer";
import { motion, useAnimation } from "framer-motion";
export default function ValuesSection() {
const controls = useAnimation();
const [ref, inView] = useInView();
const MobileView = {};
const isMobile = window.innerWidth < 768;
if (!isMobile) {
MobileView = {
visible: { y: 0, scale: 1 },
hidden: { y: 250, scale: 0 },
};
}
useEffect(() => {
if (inView) {
controls.start("visible");
}
}, [controls, inView]);
return (
<>
<motion.div
key={value.name}
ref={ref}
animate={controls}
initial="hidden"
variants={MobileView}
>Some content</motion.div>
</>
Can you help me understand what I'm doing wrong? And if you are able to provide me with a working example, it would be great and appreciated.
Best way of using screen size in next.js projects is that you can instead use a Hook from materiial ui
that represents true or false when screen width is bigger or smaller than defined value and in my opinion it's better than the window
because it has a lot of options that you can use here is what you should do step by step
first install material ui if you didn't already
// with npm
npm install @material-ui/core
// with yarn
yarn add @material-ui/core
then import and define it inside of your component
import { useMediaQuery } from "@material-ui/core";
export default function ValuesSection() {
const IsTabletOrPhone = useMediaQuery("(max-width:1024px)");
now if you screen size is bigger than 1024px
it returns false
, otherwise it returns true
so you can use it
if (!IsTabletOrPhone) {
MobileView = {
visible: { y: 0, scale: 1 },
hidden: { y: 250, scale: 0 },
};
}
Maybe it's because i assigned it with a uppercase letter, you can try changing the name to isTabletOrPhone
with lowercase, if that didn't work try to change it to let
instead
let isTabletOrPhone = useMediaQuery("(max-width:1024px)");