0

Currently I'm trying to make a parallax effect using useEffect to manipulate my DOM elements, but this is not responsive. So currently to fix this I'm trying to get the screen width and add conditions so that whenever the screen is a particular size, it should change the DOM elements in a particular way. To get the screen width I'm using const width = window.innerWidth; but this gives me a

ReferenceError: window is not defined

I tried it on my codesandbox and it does not give me this error with the exact same code. So I have 2 questions regarding this. One is how do I get rid of this error, and two, Is there a better way to make this responsive without specifying the width of each screen and changing DOM accordingly?

CodeSandbox: https://codesandbox.io/s/laughing-pascal-vc45v?file=/src/App.js

Code:

export default function App() {
  const width = window.innerWidth;
  console.log(width);
  if(width>1000){
  useEffect(function onFirstMount() {
    const changeBackground = () => {
      let value = window.scrollY;

      let img = document.getElementById("moveLeft");
      let text = document.getElementById("moveUp");

      let imgWidth = 280;

      text.style.marginTop = "-" + value * 0.5 + "px";
      text2.style.transform = `translateX(${value * 1.3}px)`;

      if (value > 600) {
        img.style.transform = `translateX(${value * 0.8 - 480 - imgWidth}px)`;
      } else {
        img.style.transform = `translateX(-${value * 0.5}px)`;
      }

      if (value > 1400) {
        img.style.transform = `translateX(${
          -1 * (value * 0.8 - 1120) + 80 + imgWidth
        }px)`;
      }

      if (value > 1700) {
        setNumber(true);
      } else {
        setNumber(false);
      }
    };
    window.addEventListener("scroll", changeBackground);
    return () => window.removeEventListener("scroll", changeBackground);
  }, []);
}
JJM50
  • 467
  • 1
  • 7
  • 20

3 Answers3

0

Your page is Server side rendered, so from server window is undefined.

You can use below example get rid of that

const width = window?.innerWidth || yourDefaultWidth

But for better solution to get right window dimension from SSR, please check this

Ken Ha
  • 129
  • 5
0

To change your style dynamically based on browser with, it is better to use media queries in your CSS file.

@media only screen and (max-width: 200px) {
  body {
    margin-top: 20px;
  }
}

@media only screen and (max-width: 480px) {
  body {
    margin-top: 40px;
  }
}
0

On a browser, window is not defined initially. When you render your component, its defined. So for the initial option, we should avoid to use it.

So if you are using window.innerWitdh in hooks or in any functions, it works. If you should use it for the initial state, you can use this alternatively.

document.documentElement.clientWidth

You can use like this.

const width = document.documentElement.clientWidth
Piece
  • 708
  • 13
  • 15