Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

remove elements by javascript without content shift

I created a chrome extension which is used to block advertisements elements from some websites.
My content script is as below:

var selectors = [
            ...
        ];
for(var i in selectors){
    if(selectors.hasOwnProperty(i)){
          var elements = document.querySelectorAll(selectors[i]);
          console.log('elements: ', elements);
          for (var k in elements) {
              if (elements.hasOwnProperty(k)) {
                   elements[k].parentElement.removeChild(elements[k]);
              }
          }
     }
}

when I wrap the code in document.addEventListener("DOMContentLoaded", function() {}, it shift the content and when I don’t wrap the code in DOMContentLoaded the elements list is empty.
what should I do to remove the advertisement element without content shift?

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

>Solution :

Rather than waiting for the whole document to load, you could consider inserting a <style> tag immediately, and have rules inside that hide those selectors.

const selectors = [ ... ];
// run ASAP:
document.body.appendChild(document.createElement('style'))
  .textContent = selectors.join(', ') + ' { display: none }';
// Run after document loads:
document.addEventListener("DOMContentLoaded", () => {
  // ...
});

This will result in a <style> tag with content like

.ad1, .ad2, .ad3 { display: none }

This way, the removal of the bad elements won’t result in content shifting, for the most part, because they already have display: none.

Another benefit of such a stylesheet is that it’ll take effect immediately, without any additional JavaScript, whenever an element is inserted. So, for example, if a page inserts an ad somewhere every 30 seconds, the CSS rules in the <style> can prevent it from being seen without having to have additional JS to deal with the dynamically generated content.

Arguably, if you just hide the ads with the stylesheet, that may be all you need to accomplish. You can additionally remove them from the DOM entirely if you want (perhaps lowering bandwidth usage), but the user probably won’t notice a difference between hidden ads and removed ads.

A MutationObserver attached on pageload is another option – instead of waiting for everything to finish first, you can remove blacklisted elements as soon as they get inserted into the DOM.

Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading