Repository: darkreader/darkreader
Pull request #1655 (2019-10-23 14:56:46)

Remove twitch.tv
Theyre using black background and pure white, blinding font color. No reason not to be able to change that to more toned and easy on the eyes version like we could all along until recently.

IamGreen112: Agreed. Made an account on here just to comment because when I went on twitch I was blinded by how bright it was and had to manually set it to dark mode on the site. Don't see why we're forced to  use their ugly option. 
TG4LAaron: There is the builds all i did was remove twitch from the list
[build.zip](https://github.com/darkreader/darkreader/files/3763827/build.zip)
[build-firefox.zip](https://github.com/darkreader/darkreader/files/3763828/build-firefox.zip)


Patch:
diff --git a/src/background/extension.ts b/src/background/extension.ts
index a2be67b2..c138273c 100644
--- a/src/background/extension.ts
+++ b/src/background/extension.ts
@@ -1,7 +1,7 @@
 import ConfigManager from './config-manager';
 import DevTools from './devtools';
 import IconManager from './icon-manager';
-import Messenger from './messenger';
+import Messenger, {ExtensionAdapter} from './messenger';
 import Newsmaker from './newsmaker';
 import TabManager from './tab-manager';
 import UserStorage from './user-storage';
@@ -100,7 +100,7 @@ export class Extension {
 
     private popupOpeningListener: () => void = null;
 
-    private getMessengerAdapter() {
+    private getMessengerAdapter(): ExtensionAdapter {
         return {
             collect: async () => {
                 if (!this.ready) {
@@ -118,7 +118,7 @@ export class Extension {
             changeSettings: (settings) => this.changeSettings(settings),
             setTheme: (theme) => this.setTheme(theme),
             setShortcut: ({command, shortcut}) => this.setShortcut(command, shortcut),
-            toggleSitePattern: (pattern) => this.toggleSitePattern(pattern),
+            toggleURL: (url) => this.toggleURL(url),
             markNewsAsRead: (ids) => this.news.markAsRead(...ids),
             onPopupOpen: () => this.popupOpeningListener && this.popupOpeningListener(),
             applyDevDynamicThemeFixes: (text) => this.devtools.applyDynamicThemeFixes(text),
@@ -282,15 +282,23 @@ export class Extension {
         this.messenger.reportChanges(info);
     }
 
-    toggleSitePattern(pattern: string) {
-        const siteList = this.user.settings.siteList.slice();
+    toggleURL(url: string) {
+        const isInDarkList = isURLInList(url, this.config.DARK_SITES);
+        const siteList = isInDarkList ?
+            this.user.settings.siteListEnabled.slice() :
+            this.user.settings.siteList.slice();
+        const pattern = getURLHost(url);
         const index = siteList.indexOf(pattern);
         if (index < 0) {
             siteList.push(pattern);
         } else {
             siteList.splice(index, 1);
         }
-        this.changeSettings({siteList});
+        if (isInDarkList) {
+            this.changeSettings({siteListEnabled: siteList});
+        } else {
+            this.changeSettings({siteList});
+        }
     }
 
     /**
@@ -299,8 +307,7 @@ export class Extension {
      */
     async toggleCurrentSite() {
         const url = await this.tabs.getActiveTabURL();
-        const host = getURLHost(url);
-        this.toggleSitePattern(host);
+        this.toggleURL(url);
     }
 
 
diff --git a/src/background/messenger.ts b/src/background/messenger.ts
index 15856afd..510db154 100644
--- a/src/background/messenger.ts
+++ b/src/background/messenger.ts
@@ -1,13 +1,13 @@
 import {ExtensionData, FilterConfig, TabInfo, Message, UserSettings} from '../definitions';
 
-interface ExtensionAdapter {
+export interface ExtensionAdapter {
     collect: () => Promise<ExtensionData>;
     getActiveTabInfo: () => Promise<TabInfo>;
     changeSettings: (settings: Partial<UserSettings>) => void;
     setTheme: (theme: Partial<FilterConfig>) => void;
     setShortcut: ({command, shortcut}) => void;
     markNewsAsRead: (ids: string[]) => void;
-    toggleSitePattern: (pattern: string) => void;
+    toggleURL: (pattern: string) => void;
     onPopupOpen: () => void;
     applyDevDynamicThemeFixes: (json: string) => Error;
     resetDevDynamicThemeFixes: () => void;
@@ -62,8 +62,8 @@ export default class Messenger {
                 this.adapter.setShortcut(data);
                 break;
             }
-            case 'toggle-site-pattern': {
-                this.adapter.toggleSitePattern(data);
+            case 'toggle-url': {
+                this.adapter.toggleURL(data);
                 break;
             }
             case 'mark-news-as-read': {
diff --git a/src/background/user-storage.ts b/src/background/user-storage.ts
index 8d8ad52b..2481f87a 100644
--- a/src/background/user-storage.ts
+++ b/src/background/user-storage.ts
@@ -25,6 +25,7 @@ export default class UserStorage {
             },
             customThemes: [],
             siteList: [],
+            siteListEnabled: [],
             applyToListedOnly: false,
             changeBrowserTheme: false,
             notifyOfNews: false,
diff --git a/src/config/dark-sites.config b/src/config/dark-sites.config
index 0237e112..90dda1bb 100644
--- a/src/config/dark-sites.config
+++ b/src/config/dark-sites.config
@@ -49,6 +49,7 @@ di.fm
 diablo3.com
 diablo3ladder.com
 discuss.noisebridge.info
+docs.docker.com
 dota2.com
 dota2.ru
 dotabuff.com
@@ -168,7 +169,6 @@ thealiendrew.github.io
 toneden.io
 totalwarwarhammer.gamepedia.com
 trustreaming.tv
-twitch.tv
 ufplanets.com
 undergroundcellar.com
 undertale.com
diff --git a/src/config/dynamic-theme-fixes.config b/src/config/dynamic-theme-fixes.config
index 43b1c7c6..7c324c13 100644
--- a/src/config/dynamic-theme-fixes.config
+++ b/src/config/dynamic-theme-fixes.config
@@ -440,6 +440,15 @@ INVERT
 
 ================================
 
+giveawayoftheday.com
+
+CSS
+.countdown-amount .diggit {
+    background: url(/images/sprite.png) 0 0 no-repeat !important;
+}
+
+================================
+
 google.*/maps
 google.*.*/maps
 
diff --git a/src/definitions.d.ts b/src/definitions.d.ts
index 208adc13..1337a945 100644
--- a/src/definitions.d.ts
+++ b/src/definitions.d.ts
@@ -21,7 +21,7 @@ export interface ExtensionActions {
     changeSettings(settings: Partial<UserSettings>);
     setTheme(theme: Partial<FilterConfig>);
     setShortcut(command: string, shortcut: string);
-    toggleSitePattern(pattern: string);
+    toggleURL(url: string);
     markNewsAsRead(ids: string[]);
     applyDevDynamicThemeFixes(text: string): Promise<void>;
     resetDevDynamicThemeFixes();
@@ -59,6 +59,7 @@ export interface UserSettings {
     theme: FilterConfig;
     customThemes: CustomSiteConfig[];
     siteList: string[];
+    siteListEnabled: string[];
     applyToListedOnly: boolean;
     changeBrowserTheme: boolean;
     notifyOfNews: boolean;
diff --git a/src/ui/connect/connector.ts b/src/ui/connect/connector.ts
index 1fffdfe1..cfd0f4c0 100644
--- a/src/ui/connect/connector.ts
+++ b/src/ui/connect/connector.ts
@@ -65,8 +65,8 @@ export default class Connector implements ExtensionActions {
         this.port.postMessage({type: 'set-theme', data: theme});
     }
 
-    toggleSitePattern(pattern: string) {
-        this.port.postMessage({type: 'toggle-site-pattern', data: pattern});
+    toggleURL(url: string) {
+        this.port.postMessage({type: 'toggle-url', data: url});
     }
 
     markNewsAsRead(ids: string[]) {
diff --git a/src/ui/connect/mock.ts b/src/ui/connect/mock.ts
index 083fd64e..25e3c919 100644
--- a/src/ui/connect/mock.ts
+++ b/src/ui/connect/mock.ts
@@ -1,3 +1,4 @@
+import {getURLHost} from '../../utils/url';
 import {ExtensionData, TabInfo, UserSettings} from '../../definitions';
 
 export function getMockData(override = {}): ExtensionData {
@@ -20,6 +21,7 @@ export function getMockData(override = {}): ExtensionData {
             },
             customThemes: [],
             siteList: [],
+            siteListEnabled: [],
             applyToListedOnly: false,
             changeBrowserTheme: false,
             notifyOfNews: false,
@@ -92,10 +94,11 @@ export function createConnectorMock() {
             Object.assign(data.shortcuts, {[command]: shortcut});
             listener(data);
         },
-        toggleSitePattern(pattern) {
+        toggleURL(url) {
+            const pattern = getURLHost(url);
             const index = data.settings.siteList.indexOf(pattern);
             if (index >= 0) {
-                data.settings.siteList.splice(pattern, 1);
+                data.settings.siteList.splice(index, 1, pattern);
             } else {
                 data.settings.siteList.push(pattern);
             }
diff --git a/src/ui/popup/components/custom-settings-toggle/index.tsx b/src/ui/popup/components/custom-settings-toggle/index.tsx
index 74b52e1d..ae46d507 100644
--- a/src/ui/popup/components/custom-settings-toggle/index.tsx
+++ b/src/ui/popup/components/custom-settings-toggle/index.tsx
@@ -23,7 +23,7 @@ export default function CustomSettingsToggle({data, tab, actions}: ExtWrapper &
             class={{
                 'custom-settings-toggle': true,
                 'custom-settings-toggle--checked': isCustom,
-                'custom-settings-toggle--disabled': tab.isProtected || (tab.isInDarkList && !data.settings.applyToListedOnly),
+                'custom-settings-toggle--disabled': tab.isProtected,
             }}
             onclick={(e) => {
                 if (isCustom) {
diff --git a/src/ui/popup/components/site-toggle/index.tsx b/src/ui/popup/components/site-toggle/index.tsx
index 02c9c496..8c1cd9b0 100644
--- a/src/ui/popup/components/site-toggle/index.tsx
+++ b/src/ui/popup/components/site-toggle/index.tsx
@@ -7,8 +7,7 @@ import {ExtWrapper, TabInfo} from '../../../../definitions';
 export default function SiteToggleButton({data, tab, actions}: ExtWrapper & {tab: TabInfo}) {
     const toggleHasEffect = (
         data.isEnabled &&
-        !tab.isProtected &&
-        (data.settings.applyToListedOnly || !tab.isInDarkList)
+        !tab.isProtected
     );
     const isSiteEnabled = isURLEnabled(tab.url, data.settings, tab);
     const host = getURLHost(tab.url || '');
@@ -29,7 +28,7 @@ export default function SiteToggleButton({data, tab, actions}: ExtWrapper & {tab
                 'site-toggle--active': isSiteEnabled,
                 'site-toggle--disabled': !toggleHasEffect
             }}
-            onclick={() => actions.toggleSitePattern(host)}
+            onclick={() => actions.toggleURL(tab.url)}
         >
             <span class="site-toggle__mark"><CheckmarkIcon isEnabled={isSiteEnabled} /></span>
             {' '}
diff --git a/src/utils/url.ts b/src/utils/url.ts
index f44fffce..5395384a 100644
--- a/src/utils/url.ts
+++ b/src/utils/url.ts
@@ -104,5 +104,11 @@ export function isURLEnabled(url: string, userSettings: UserSettings, {isProtect
     if (userSettings.applyToListedOnly) {
         return isURLInUserList;
     }
+    // TODO: Use `siteListEnabled`, `siteListDisabled`, `enabledByDefault` options.
+    // Delete `siteList` and `applyToListedOnly` options, transfer user's values.
+    const isURLInEnabledList = isURLInList(url, userSettings.siteListEnabled);
+    if (isURLInEnabledList && isInDarkList) {
+        return true;
+    }
     return (!isInDarkList && !isURLInUserList);
 }


Test patch:
diff --git a/tests/url.tests.ts b/tests/url.tests.ts
index 748bb6ec..ca6b1d46 100644
--- a/tests/url.tests.ts
+++ b/tests/url.tests.ts
@@ -5,76 +5,93 @@ test('URL is enabled', () => {
     // Not invert listed
     expect(isURLEnabled(
         'https://mail.google.com/mail/u/0/',
-        {siteList: ['google.com'], applyToListedOnly: false} as UserSettings,
+        {siteList: ['google.com'], siteListEnabled: [], applyToListedOnly: false} as UserSettings,
         {isProtected: false, isInDarkList: false},
     )).toBe(false);
     expect(isURLEnabled(
         'https://mail.google.com/mail/u/0/',
-        {siteList: ['mail.google.com'], applyToListedOnly: false} as UserSettings,
+        {siteList: ['mail.google.com'], siteListEnabled: [], applyToListedOnly: false} as UserSettings,
         {isProtected: false, isInDarkList: false},
     )).toBe(false);
     expect(isURLEnabled(
         'https://mail.google.com/mail/u/0/',
-        {siteList: ['mail.google.*'], applyToListedOnly: false} as UserSettings,
+        {siteList: ['mail.google.*'], siteListEnabled: [], applyToListedOnly: false} as UserSettings,
         {isProtected: false, isInDarkList: false},
     )).toBe(false);
     expect(isURLEnabled(
         'https://mail.google.com/mail/u/0/',
-        {siteList: ['mail.google.*/mail'], applyToListedOnly: false} as UserSettings,
+        {siteList: ['mail.google.*/mail'], siteListEnabled: [], applyToListedOnly: false} as UserSettings,
         {isProtected: false, isInDarkList: false},
     )).toBe(false);
     expect(isURLEnabled(
         'https://mail.google.com/mail/u/0/',
-        {siteList: [], applyToListedOnly: false} as UserSettings,
+        {siteList: [], siteListEnabled: [], applyToListedOnly: false} as UserSettings,
         {isProtected: false, isInDarkList: false},
     )).toBe(true);
     expect(isURLEnabled(
         'https://mail.google.com/mail/u/0/',
-        {siteList: ['google.com/maps'], applyToListedOnly: false} as UserSettings,
+        {siteList: ['google.com/maps'], siteListEnabled: [], applyToListedOnly: false} as UserSettings,
         {isProtected: false, isInDarkList: false},
     )).toBe(true);
 
     // Invert listed only
     expect(isURLEnabled(
         'https://mail.google.com/mail/u/0/',
-        {siteList: ['google.com'], applyToListedOnly: true} as UserSettings,
+        {siteList: ['google.com'], siteListEnabled: [], applyToListedOnly: true} as UserSettings,
         {isProtected: false, isInDarkList: false},
     )).toBe(true);
     expect(isURLEnabled(
         'https://mail.google.com/mail/u/0/',
-        {siteList: ['google.*/mail'], applyToListedOnly: true} as UserSettings,
+        {siteList: ['google.*/mail'], siteListEnabled: [], applyToListedOnly: true} as UserSettings,
         {isProtected: false, isInDarkList: false},
     )).toBe(true);
     expect(isURLEnabled(
         'https://mail.google.com/mail/u/0/',
-        {siteList: [], applyToListedOnly: true} as UserSettings,
+        {siteList: [], siteListEnabled: [], applyToListedOnly: true} as UserSettings,
         {isProtected: false, isInDarkList: false},
     )).toBe(false);
     expect(isURLEnabled(
         'https://mail.google.com/mail/u/0/',
-        {siteList: ['google.com/maps'], applyToListedOnly: true} as UserSettings,
+        {siteList: ['google.com/maps'], siteListEnabled: [], applyToListedOnly: true} as UserSettings,
         {isProtected: false, isInDarkList: false},
     )).toBe(false);
 
     // Special URLs
     expect(isURLEnabled(
         'https://chrome.google.com/webstore',
-        {siteList: ['chrome.google.com'], applyToListedOnly: false} as UserSettings,
+        {siteList: ['chrome.google.com'], siteListEnabled: [], applyToListedOnly: false} as UserSettings,
         {isProtected: true, isInDarkList: false},
     )).toBe(false);
     expect(isURLEnabled(
         'https://chrome.google.com/webstore',
-        {siteList: ['chrome.google.com'], applyToListedOnly: true} as UserSettings,
+        {siteList: ['chrome.google.com'], siteListEnabled: [], applyToListedOnly: true} as UserSettings,
         {isProtected: true, isInDarkList: false},
     )).toBe(false);
     expect(isURLEnabled(
         'https://darkreader.org/',
-        {siteList: [], applyToListedOnly: false} as UserSettings,
+        {siteList: [], siteListEnabled: [], applyToListedOnly: false} as UserSettings,
         {isProtected: false, isInDarkList: true},
     )).toBe(false);
     expect(isURLEnabled(
         'https://darkreader.org/',
-        {siteList: ['darkreader.org'], applyToListedOnly: true} as UserSettings,
+        {siteList: ['darkreader.org'], siteListEnabled: [], applyToListedOnly: true} as UserSettings,
         {isProtected: false, isInDarkList: true},
     )).toBe(true);
+
+    // Temporary Dark Sites list fix
+    expect(isURLEnabled(
+        'https://darkreader.org/',
+        {siteList: [], siteListEnabled: ['darkreader.org'], applyToListedOnly: false} as UserSettings,
+        {isProtected: false, isInDarkList: true},
+    )).toBe(true);
+    expect(isURLEnabled(
+        'https://darkreader.org/',
+        {siteList: [], siteListEnabled: [], applyToListedOnly: false} as UserSettings,
+        {isProtected: false, isInDarkList: true},
+    )).toBe(false);
+    expect(isURLEnabled(
+        'https://google.com/',
+        {siteList: [], siteListEnabled: ['darkreader.org'], applyToListedOnly: false} as UserSettings,
+        {isProtected: false, isInDarkList: false},
+    )).toBe(true);
 });