Add ability to linger for remove-attr scriplet · gorhill/uBlock@0f330c7 (original) (raw)

Original file line number Diff line number Diff line change
@@ -665,7 +665,10 @@
665 665 if ( selector === '' |
666 666 selector = `[${tokens.join('],[')}]`;
667 667 }
668 -const rmattr = function() {
668 +let behavior = '{{3}}';
669 +let timer;
670 +const rmattr = ( ) => {
671 +timer = undefined;
669 672 try {
670 673 const nodes = document.querySelectorAll(selector);
671 674 for ( const node of nodes ) {
@@ -676,10 +679,39 @@
676 679 } catch(ex) {
677 680 }
678 681 };
679 -if ( document.readyState === 'loading' ) {
680 -window.addEventListener('DOMContentLoaded', rmattr, { once: true });
681 -} else {
682 +const mutationHandler = mutations => {
683 +if ( timer !== undefined ) { return; }
684 +let skip = true;
685 +for ( let i = 0; i < mutations.length && skip; i++ ) {
686 +const { type, addedNodes, removedNodes } = mutations[i];
687 +if ( type === 'attributes' ) { skip = false; }
688 +for ( let j = 0; j < addedNodes.length && skip; j++ ) {
689 +if ( addedNodes[j].nodeType === 1 ) { skip = false; break; }
690 +}
691 +for ( let j = 0; j < removedNodes.length && skip; j++ ) {
692 +if ( removedNodes[j].nodeType === 1 ) { skip = false; break; }
693 +}
694 +}
695 +if ( skip ) { return; }
696 +timer = self.requestIdleCallback(rmattr, { timeout: 67 });
697 +};
698 +const start = ( ) => {
682 699 rmattr();
700 +if ( /\bstay\b/.test(behavior) === false ) { return; }
701 +const observer = new MutationObserver(mutationHandler);
702 +observer.observe(document.documentElement, {
703 +attributes: true,
704 +attributeFilter: tokens,
705 +childList: true,
706 +subtree: true,
707 +});
708 +};
709 +if ( document.readyState !== 'complete' && /\bcomplete\b/.test(behavior) ) {
710 +document.addEventListener('load', start, { once: true });
711 +} else if ( document.readyState === 'loading' ) {
712 +document.addEventListener('DOMContentLoaded', start, { once: true });
713 +} else {
714 +start();
683 715 }
684 716 })();
685 717