admin管理员组

文章数量:1193389

I am using this plugin - isOnScreen to check whether an element is visible on the viewport (to check if posts has been viewed or not).

But is it possible to have a callback of some sort so that instead of having a setTimeOut and checking the visibility of each and every post every time, fire a callback when the respective element is visible?

Or is there any other library I can use to do this?

I am talking about the visual viewport. (Not css visibility)

I am using this plugin - isOnScreen to check whether an element is visible on the viewport (to check if posts has been viewed or not).

But is it possible to have a callback of some sort so that instead of having a setTimeOut and checking the visibility of each and every post every time, fire a callback when the respective element is visible?

Or is there any other library I can use to do this?

I am talking about the visual viewport. (Not css visibility)

Share Improve this question edited Dec 19, 2015 at 15:34 Vidya Sagar 1,7193 gold badges17 silver badges30 bronze badges asked Dec 19, 2015 at 15:01 Vignesh T.V.Vignesh T.V. 1,8604 gold badges30 silver badges50 bronze badges 10
  • 1 I really think this is not a duplicate of that question. This is to check whether or not an element is currently visible in the viewport. – jianweichuah Commented Dec 19, 2015 at 15:09
  • 1 anyway, I think one easy way to do it can be listening to the scroll event and have this check in there. $(window).scroll(function() { if ($('selector').isOnScreen()) {console.log("element has been seen!")} }); – jianweichuah Commented Dec 19, 2015 at 15:13
  • 1 You can subsribe to scroll and resize events and only check visibility on these events. This only works if your page is more or less static. If elements move around (for example when an element above disappears) this does not work. – lex82 Commented Dec 19, 2015 at 15:13
  • 1 @benjamin-gruenbaum, as mentioned above, this is not a duplicated question. This question is related to whether an element is on the viewport. The other is about whether the element is visible. Could you unmark as duplicated? – Darlesson Commented Dec 27, 2018 at 6:18
  • 1 @Darlesson done, I think it's now sufficiently different and this can be neatly answered with intersectionobserver – Benjamin Gruenbaum Commented Dec 27, 2018 at 9:18
 |  Show 5 more comments

3 Answers 3

Reset to default 21

Here is a script returning a promise using the new IntersectionObserver API for checking whether or not an element is actually visible in the viewport:

function isVisible(domElement) {
  return new Promise(resolve => {
    const o = new IntersectionObserver(([entry]) => {
      resolve(entry.intersectionRatio === 1);
      o.disconnect();
    });
    o.observe(domElement);
  });
}

Which you can use in your code:

const visible = await isVisible(document.querySelector('#myElement'));
console.log(visible);

There are mainly two ways to check if an element is visible/hidden on the screen during scrolling:

  1. Listening to the window scroll event.
  2. Observing the element for visibility using Intersection Observer API.

Scroll events have a lot of performance issues.

The new way is using Intersection Observer API. Intersection Observer API makes it possible to know when an element enters or exits the browser viewport. This API is asynchronous

var observer = new IntersectionObserver(function(entries) {
    if(entries[0].isIntersecting === true)
        console.log('Element is fully visible in screen');
}, { threshold: [1] });

observer.observe(document.querySelector("#element"));

Threshold is a number between 0 and 1, that represents the viewable area of the target element in the screen. For example, 0 represents no area of element is visible. A value of 0.10 represents about 10% area is viewable in the screen. Value of 1 means element is fully viewable in the screen.

I recently worked on a small library that checks when an element is on the viewport called viewport-action. It could be handy for cases like yours.

Feel details to consider:

  • You can have the callback called once or every time.
  • You can check how much of the element is shown by checking when a certain height, width or area is shown.
  • It waits for the DOMContentLoaded event in browsers or deviceready in Cordova apps before starting checking for elements (in case it's a Cordova app).
  • It doesn't depend on Promise (yet) to support applications without it and older browsers.

See the example below where it checks for how much of the element is shown based on percentage.

var options = {
    once: true
};

viewportAction.add('#check', function (e) {
 
    var percentageShown = (e.detail.availableArea / (e.detail.width * e.detail.height)) * 100;
 
    // Load an image inside the element when the area visible is bigger
    // than 60% of its area.
    if (percentageShown > 60) {
 
        e.target.innerText = 'Showing ' + percentageShown.toFixed(0) + '% of the element';
 
        // Remove handler if you don't want to use options
        // e.removeHandler();
    } else {
      e.target.innerText = 'Showing less than 60%';
    }
    
// Use options, optionally
//}, options);
});
#check {
  background-color: #F00;
  color: #FFF;
  height:500px;
  width; 100%;
}

.spacer {
  background-color: #CCC;
  height: 300px;
}
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/viewportAction.min.js"></script>

<div class="spacer">Scroll down or up</div>

<div id="check"></div>

<div class="spacer"></div>

本文标签: javascriptCheck if an element is visible on screenStack Overflow