| Index: lib/content/elemHideEmulation.js |
| =================================================================== |
| --- a/lib/content/elemHideEmulation.js |
| +++ b/lib/content/elemHideEmulation.js |
| @@ -395,52 +395,85 @@ |
| return pattern.selectors.some(s => s.dependsOnDOM); |
| } |
| function patternDependsOnStylesAndDOM(pattern) |
| { |
| return pattern.selectors.some(s => s.dependsOnStyles && s.dependsOnDOM); |
| } |
| -function filterPatterns(patterns, {stylesheets, mutations}) |
| -{ |
| - if (stylesheets && !mutations) |
| - return patterns.filter(patternDependsOnStyles); |
| - |
| - if (!stylesheets && mutations) |
| - return patterns.filter(patternDependsOnDOM); |
| - |
| - return patterns.slice(); |
| -} |
| - |
| -function shouldObserveAttributes(patterns) |
| +function patternMaybeDependsOnAttributes(pattern) |
| { |
| // Observe changes to attributes if either there's a plain selector that |
| // looks like an ID selector, class selector, or attribute selector in one of |
| // the patterns (e.g. "a[href='https://example.com/']") |
| // or there's a properties selector nested inside a has selector |
| // (e.g. "div:-abp-has(:-abp-properties(color: blue))") |
| - return patterns.some( |
| - pattern => pattern.selectors.some( |
| - selector => selector.maybeDependsOnAttributes || |
| - (selector instanceof HasSelector && |
| - selector.dependsOnStyles) |
| - ) |
| + return pattern.selectors.some( |
|
Manish Jethani
2018/03/02 13:23:42
One obvious optimization is that a pattern can rem
|
| + selector => selector.maybeDependsOnAttributes || |
| + (selector instanceof HasSelector && |
| + selector.dependsOnStyles) |
| ); |
| } |
| +function patternDependsOnCharacterData(pattern) |
| +{ |
| + // Observe changes to character data only if there's a contains selector in |
| + // one of the patterns. |
| + return pattern.selectors.some(selector => selector.dependsOnCharacterData); |
| +} |
| + |
| +function patternMatchesMutationTypes(pattern, mutationTypes) |
| +{ |
| + return mutationTypes.has("childList") || |
| + (mutationTypes.has("attributes") && |
| + patternMaybeDependsOnAttributes(pattern)) || |
| + (mutationTypes.has("characterData") && |
| + patternDependsOnCharacterData(pattern)); |
| +} |
| + |
| +function extractMutationTypes(mutations) |
| +{ |
| + let types = new Set(); |
| + |
| + for (let mutation of mutations) |
| + { |
| + types.add(mutation.type); |
| + |
| + // There are only 3 types of mutations: "attributes", "characterData", and |
| + // "childList". |
| + if (types.size == 3) |
| + break; |
| + } |
| + |
| + return types; |
| +} |
| + |
| +function filterPatterns(patterns, {stylesheets, mutations}) |
| +{ |
| + if (!stylesheets && !mutations) |
|
Manish Jethani
2018/03/02 13:23:42
Do full processing.
|
| + return patterns.slice(); |
| + |
| + let mutationTypes = mutations ? extractMutationTypes(mutations) : null; |
| + |
| + return patterns.filter(pattern => |
| + (stylesheets && patternDependsOnStyles(pattern)) || |
| + (mutations && patternDependsOnDOM(pattern) && |
| + patternMatchesMutationTypes(pattern, mutationTypes)) |
| + ); |
| +} |
| + |
| +function shouldObserveAttributes(patterns) |
| +{ |
| + return patterns.some(patternMaybeDependsOnAttributes); |
| +} |
| + |
| function shouldObserveCharacterData(patterns) |
| { |
| - // Observe changes to character data only if there's a contains selector in |
| - // one of the patterns. |
| - return patterns.some( |
| - pattern => pattern.selectors.some( |
| - selector => selector.dependsOnCharacterData |
| - ) |
| - ); |
| + return patterns.some(patternDependsOnCharacterData); |
| } |
| function ElemHideEmulation(addSelectorsFunc, hideElemsFunc) |
| { |
| this.document = document; |
| this.addSelectorsFunc = addSelectorsFunc; |
| this.hideElemsFunc = hideElemsFunc; |
| this.observer = new MutationObserver(this.observe.bind(this)); |