Skip to content
Advertisement

Why is my intersectionObserver returning my querySelect as undefined?

I am attempting to target a parent element and a child element using an intersectionObserver, then I have a function changing the background of the parent to a different color and rotating the child element.

This code works on the parent div, however the child item returns as undefined. Am I unable to target child elements with querySelector, or is the intersectionObserver unable to observe more than one element?

let options = {
  threshold: 0.25
}

let observer = new IntersectionObserver(function(entries, observer) {
  entries.forEach(entry => {
    if (!entry.isIntersecting) {
      return;
    } else {
      console.log(entry.target);
      console.log(entry.sticky);
      alert('INTERSECTING!');
      entry.target.classList.toggle("red");
      entry.sticky.classList.toggle("rotate");
    }
  });
}, options);

let target = document.querySelector('.placeholder__div__large');
let sticky = document.querySelector('.sticky__container');

observer.observe(target, sticky);
.placeholder__div__large {
  height: 200vh;
  width: 100vw;
  display: flex;
  align-items: center;
  justify-content: center;
  color: white;
  background: black;
  transition: 2s;
}

.sticky__container {
  position: sticky;
  top: 100px;
  width: 200px;
  height: 200px;
}

.sticky__item {
  display: flex;
  justify-content: center;
  align-items: center;
  text-align: center;
  background: white;
  color: black;
  width: 100%;
  height: 100%;
}

.red {
  background: red;
  transition: 2s;
}

.rotate {
  transform: rotate(180deg);
}
<div class="placeholder__div__large">
  <div class="sticky__container">
    <div class="sticky__item">STICKY ITEM</div>
  </div>
</div>

Advertisement

Answer

You can’t observe multiple elements by passing them all to .observe, you have to call it multiple times.

Also, I assume you rather wanted to do it like this (I’m not sure if I’m right, but parts of your code didn’t make any sense to me):

let options = {
  threshold: 0.25
}

const observer = new IntersectionObserver(function(entries, observer) {
  entries.forEach(entry => {
    console.log('INTERSECTING with', entry.target, entry.isIntersecting);
    entry.target.classList.toggle("intersect", entry.isIntersecting);
  });
}, options);

const target = document.querySelector('.placeholder__div__large');
const sticky = document.querySelector('.sticky__container');

observer.observe(target);
observer.observe(sticky);
.placeholder__div__large {
  height: 200vh;
  width: 100vw;
  display: flex;
  align-items: center;
  justify-content: center;
  color: white;
  background: black;
  transition: 2s;
}

.sticky__container {
  position: sticky;
  top: 100px;
  width: 200px;
  height: 200px;
}

.sticky__item {
  display: flex;
  justify-content: center;
  align-items: center;
  text-align: center;
  background: white;
  color: black;
  width: 100%;
  height: 100%;
}

.red-whenintersect.intersect {
  background: red;
  transition: 2s;
}

.rotate-whenintersect.intersect {
  transform: rotate(180deg);
}
<div class="placeholder__div__large red-whenintersect">
  <div class="sticky__container">
    <div class="sticky__item rotate-whenintersect">STICKY ITEM</div>
  </div>
</div>
User contributions licensed under: CC BY-SA
4 People found this is helpful
Advertisement