简体   繁体   中英

How to get elements in headless browser inside a bounding box

I have a use case where I need the user to mark a bounding box on a web page and using PhantomJS or CasperJS I would like to get the elements that are covered or touched by this box.

Is that doable and if so how?

It is fairly easy to iterate over all elements of the page, get their bounding box and see if that bounding box is inside of the given box:

var rectExample = {
  top: 0,
  left: 0,
  width: 500,
  height: 100
};
casper.evaluate(function(rect) {
  rect.top -= window.scrollY;
  rect.left -= window.scrollX;
  var all = document.querySelectorAll('*');
  var filtered = Array.prototype.filter.call(all, function (el) {
    var elRect = el.getBoundingClientRect();
    return elRect.width > 0
      && elRect.height > 0
      && rect.width >= elRect.width 
      && rect.height >= elRect.height 
      && rect.top <= elRect.top 
      && rect.left <= elRect.left 
      && (rect.top + rect.height) >= (elRect.top + elRect.height) 
      && (rect.left + rect.width) >= (elRect.left + elRect.width);
  });

  filtered.forEach(function(el){
    // TODO: do something with the element that is inside of the rectangle
  });
}, rectExample);

Note that getBoundingClientRect returns a rectangle adjusted to the current scroll position. Therefore the given rectangle is adjusted by the current scroll position in order to make the comparisons in the same coordinate system.

Note that it is not possible to return DOM elements from the page context (inside of casper.evaluate ) to the outside. You will have to work with those elements inside and return only a serializable representation of that data. You can use normal console.log calls inside of casper.evaluate , but you have to register to the "remote.message" event in order to see them.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM