☰

ImageFap Dark Mode

Dark theme for ImageFap with a toggle.

Tendrás que instalar una extensión para tu navegador como Tampermonkey, Greasemonkey o Violentmonkey si quieres utilizar este script.

You will need to install an extension such as Tampermonkey or Violentmonkey to install this script.

Tendrás que instalar una extensión como Tampermonkey o Violentmonkey para instalar este script.

Necesitarás instalar una extensión como Tampermonkey o Userscripts para instalar este script.

Tendrás que instalar una extensión como Tampermonkey antes de poder instalar este script.

Necesitarás instalar una extensión para administrar scripts de usuario si quieres instalar este script.

(Ya tengo un administrador de scripts de usuario, déjame instalarlo)

Tendrás que instalar una extensión como Stylus antes de poder instalar este script.

Tendrás que instalar una extensión como Stylus antes de poder instalar este script.

Tendrás que instalar una extensión como Stylus antes de poder instalar este script.

Para poder instalar esto tendrás que instalar primero una extensión de estilos de usuario.

Para poder instalar esto tendrás que instalar primero una extensión de estilos de usuario.

Para poder instalar esto tendrás que instalar primero una extensión de estilos de usuario.

(Ya tengo un administrador de estilos de usuario, déjame instalarlo)

// ==UserScript==
// @name         ImageFap Dark Mode
// @namespace    imagefap@nereids
// @version      1.0.0
// @description  Dark theme for ImageFap with a toggle.
// @author       nereids
// @license      MIT
// @match        *://imagefap.com/*
// @match        *://*.imagefap.com/*
// @icon         https://icons.duckduckgo.com/ip3/imagefap.com.ico
// @run-at       document-start
// @grant        none
// ==/UserScript==

(function () {
    'use strict';

    // Set to true to desaturate photos and video as well. The chrome is always grayscale.
    var GRAYSCALE_MEDIA = false;

    var STORAGE_KEY = 'if-dark-mode';

    function isOn() {
        try {
            var v = localStorage.getItem(STORAGE_KEY);
            return v === null || v === '1';
        } catch (e) {
            return true;
        }
    }

    function setOn(on) {
        try {
            localStorage.setItem(STORAGE_KEY, on ? '1' : '0');
        } catch (e) {}
    }

    var CSS = [
        'html.if-dark {',
        '  color-scheme: dark !important;',
        '  background: #141414 !important;',
        '  scrollbar-color: #4a4a4a #141414;',
        '}',
        'html.if-dark body {',
        '  background: #141414 !important;',
        '  color: #cfcfcf !important;',
        '}',
        'html.if-dark body,',
        'html.if-dark table,',
        'html.if-dark tbody,',
        'html.if-dark thead,',
        'html.if-dark tfoot,',
        'html.if-dark tr,',
        'html.if-dark td,',
        'html.if-dark th,',
        'html.if-dark div,',
        'html.if-dark span,',
        'html.if-dark p,',
        'html.if-dark font,',
        'html.if-dark center,',
        'html.if-dark li,',
        'html.if-dark ul,',
        'html.if-dark ol,',
        'html.if-dark dl,',
        'html.if-dark dt,',
        'html.if-dark dd,',
        'html.if-dark h1,',
        'html.if-dark h2,',
        'html.if-dark h3,',
        'html.if-dark h4,',
        'html.if-dark label,',
        'html.if-dark small,',
        'html.if-dark big,',
        'html.if-dark blockquote,',
        'html.if-dark pre,',
        'html.if-dark i,',
        'html.if-dark em,',
        'html.if-dark u,',
        'html.if-dark s {',
        '  background-color: transparent !important;',
        '  color: #cfcfcf !important;',
        '  border-color: #3a3a3a !important;',
        '  outline-color: #5a5a5a !important;',
        '}',
        'html.if-dark b,',
        'html.if-dark strong {',
        '  background-color: transparent !important;',
        '  color: #f2f2f2 !important;',
        '}',
        'html.if-dark hr,',
        'html.if-dark .hr {',
        '  background-color: #3a3a3a !important;',
        '  border-color: #3a3a3a !important;',
        '  color: #3a3a3a !important;',
        '}',
        'html.if-dark [class$="_hdr"],',
        'html.if-dark h1#title,',
        'html.if-dark td.colhead,',
        'html.if-dark .right_side_top,',
        'html.if-dark .our_niches,',
        'html.if-dark .announceBox .close,',
        'html.if-dark #playlist .head,',
        'html.if-dark #flag .head,',
        'html.if-dark #share .head,',
        'html.if-dark .gallerylist table tr.head,',
        'html.if-dark .gallerylist table tr.head td {',
        '  background-color: #343434 !important;',
        '  color: #f3f3f3 !important;',
        '  border-color: #4a4a4a !important;',
        '}',
        'html.if-dark [class^="blk_"]:not(a):not([class$="_hdr"]),',
        'html.if-dark #controlpanel,',
        'html.if-dark div#controlpanel div.content,',
        'html.if-dark .left_side,',
        'html.if-dark .right_side {',
        '  background-color: #1b1b1b !important;',
        '  color: #cfcfcf !important;',
        '  border-color: #3a3a3a !important;',
        '}',
        'html.if-dark .avatar {',
        '  border: none !important;',
        '  background-color: #242424 !important;',
        '  border-color: #555 !important;',
        '  color: #ddd !important;',
        '}',
        'html.if-dark .avatar .subscribers,',
        'html.if-dark .avatar .comments {',
        '  color: #cfcfcf !important;',
        '}',
        'html.if-dark img.gal_thumb,',
        'html.if-dark .gal_thumb {',
        '  border-color: #6a6a6a !important;',
        '  background-color: #111 !important;',
        '}',
        'html.if-dark #cat {',
        '  background-color: #1c1c1c !important;',
        '  border-color: #4a4a4a !important;',
        '}',
        'html.if-dark .msgCont,',
        'html.if-dark .relCont,',
        'html.if-dark .relatedgalleriescontainer,',
        'html.if-dark .relatedgalleriescontainer .relateditem,',
        'html.if-dark #flag,',
        'html.if-dark #share,',
        'html.if-dark #playlist,',
        'html.if-dark .blockwidgetpopup,',
        'html.if-dark #cat_tooltip,',
        'html.if-dark .tooltip,',
        'html.if-dark .sample_popup,',
        'html.if-dark .sample_popup div,',
        'html.if-dark .announceBox,',
        'html.if-dark div#controlpanel div.messages ul,',
        'html.if-dark div#controlpanel div.content ul.tabs,',
        'html.if-dark div#controlpanel div.content ul.tabs li a,',
        'html.if-dark div#controlpanel div.content div.tabs-content,',
        'html.if-dark div#controlpanel div.content table.list thead tr th,',
        'html.if-dark div#controlpanel div.content table.list tbody tr td,',
        'html.if-dark table.request tr td {',
        '  background-color: #262626 !important;',
        '  color: #e0e0e0 !important;',
        '  border-color: #555 !important;',
        '  box-shadow: none !important;',
        '}',
        'html.if-dark .itemCounter,',
        'html.if-dark .isblocked,',
        'html.if-dark .notblocked {',
        '  background-color: #3f3f3f !important;',
        '  color: #f5f5f5 !important;',
        '  border-color: #6a6a6a !important;',
        '}',
        'html.if-dark div#controlpanel div.content p.pagination strong {',
        '  background-color: #4a4a4a !important;',
        '  color: #ffffff !important;',
        '  border-color: #4a4a4a !important;',
        '}',
        'html.if-dark .tnaBarBlueWrap {',
        '  filter: grayscale(1) brightness(0.55) contrast(1.05);',
        '}',
        'html.if-dark a[title="ImageFap.com"] img,',
        'html.if-dark img[alt="ImageFap.com"] {',
        '  filter: invert(1) grayscale(1) contrast(1.15) !important;',
        '  background: transparent !important;',
        '}',
        'html.if-dark.if-gray-media img,',
        'html.if-dark.if-gray-media video {',
        '  filter: grayscale(1) !important;',
        '}',
        'html.if-dark.if-gray-media a[title="ImageFap.com"] img,',
        'html.if-dark.if-gray-media img[alt="ImageFap.com"] {',
        '  filter: invert(1) grayscale(1) contrast(1.15) !important;',
        '}',
        'html.if-dark input:not([type="checkbox"]):not([type="radio"]):not([type="image"]):not([type="hidden"]),',
        'html.if-dark textarea,',
        'html.if-dark select,',
        'html.if-dark button {',
        '  background-color: #1c1c1c !important;',
        '  color: #e8e8e8 !important;',
        '  border: 1px solid #5c5c5c !important;',
        '  box-shadow: none !important;',
        '}',
        'html.if-dark input::placeholder,',
        'html.if-dark textarea::placeholder {',
        '  color: #8a8a8a !important;',
        '}',
        'html.if-dark ::selection {',
        '  background: #3a3a3a !important;',
        '  color: #ffffff !important;',
        '}',
        'html.if-dark a,',
        'html.if-dark a:link,',
        'html.if-dark a:visited,',
        'html.if-dark a *,',
        'html.if-dark a font,',
        'html.if-dark a span,',
        'html.if-dark a b,',
        'html.if-dark a i,',
        'html.if-dark a u {',
        '  color: #3f75aa !important;',
        '  background-color: transparent !important;',
        '}',
        'html.if-dark a:visited,',
        'html.if-dark a:visited *,',
        'html.if-dark a:visited font,',
        'html.if-dark a:visited b {',
        '  color: #6573b1 !important;',
        '}',
        'html.if-dark a:hover,',
        'html.if-dark a:hover *,',
        'html.if-dark a:hover font,',
        'html.if-dark a:hover b {',
        '  color: #4d87c2 !important;',
        '}',
        'html.if-dark .blockwidget a,',
        'html.if-dark .blockwidget a:hover,',
        'html.if-dark .isblocked a,',
        'html.if-dark .notblocked a,',
        'html.if-dark .itemCounter a {',
        '  color: #f5f5f5 !important;',
        '}',
        'html.if-dark a[class$="_hdr"],',
        'html.if-dark a[class$="_hdr"] *,',
        'html.if-dark .gallerylist table tr.head a,',
        'html.if-dark .gallerylist table tr.head a * {',
        '  color: #6cb6ff !important;',
        '}',
        'html.if-dark .gallerylist table tbody tr * {',
        '  background-color: #141414 !important;',
        '}',
        'html.if-dark .gallerylist table tbody tr td center img {',
        '  filter: invert(1) contrast(1.05) hue-rotate(170deg) opacity(50%) !important;',
        '  background: transparent !important;',
        '}',
        'html.if-dark a[class$="_hdr"]:visited,',
        'html.if-dark a[class$="_hdr"]:visited * {',
        '  color: #9aa8e8 !important;',
        '}',
        'html.if-dark a[class$="_hdr"]:hover,',
        'html.if-dark a[class$="_hdr"]:hover *,',
        'html.if-dark .gallerylist table tr.head a:hover,',
        'html.if-dark .gallerylist table tr.head a:hover * {',
        '  color: #b9dcff !important;',
        '}',
        'html.if-dark img._lazy {',
        ' border: none !important;',
        '}',
        'html.if-dark img.gal_thumb',
        'html.if-dark img.lazy',
        'html.if-dark #mainPhoto',
        'html.if-dark #slideshow img',
        'html.if-dark #gallery img',
        'html.if-dark #_navi_cavi img',
        'html.if-dark #playlist li.thumb img {',
        '  border: 0 !important;',
        '  padding: 0 !important;',
        '  background: transparent !important;',
        '  background-color: transparent !important;',
        '  box-shadow: none !important;',
        '}',
        '#if-dark-toggle {',
        '  position: fixed !important;',
        '  right: 12px !important;',
        '  bottom: 12px !important;',
        '  z-index: 2147483647 !important;',
        '  margin: 0 !important;',
        '  padding: 6px 6px !important;',
        '  background: #2a2a2a !important;',
        '  color: #e8e8e8 !important;',
        '  border: none !important;',
        '  border-radius: 50px !important;',
        '  font: 22px/1.2 Verdana, Tahoma, sans-serif !important;',
        '  cursor: pointer !important;',
        '}',
    ].join('\n');

    function applyRoot(on) {
        var root = document.documentElement;
        if (!root) return;
        root.classList.toggle('if-dark', !!on);
        root.classList.toggle('if-gray-media', !!on && GRAYSCALE_MEDIA);
        if (!on) unpaint();
    }

    function parseColor(c) {
        if (!c) return null;
        c = String(c).trim().toLowerCase();
        var m;
        if ((m = /^#([0-9a-f]{3})$/.exec(c))) {
            return [
                parseInt(m[1].charAt(0) + m[1].charAt(0), 16),
                parseInt(m[1].charAt(1) + m[1].charAt(1), 16),
                parseInt(m[1].charAt(2) + m[1].charAt(2), 16)
            ];
        }
        if ((m = /^#([0-9a-f]{6})$/.exec(c))) {
            return [
                parseInt(m[1].slice(0, 2), 16),
                parseInt(m[1].slice(2, 4), 16),
                parseInt(m[1].slice(4, 6), 16)
            ];
        }
        if ((m = /^rgba?\(\s*(\d+)[,\s]+(\d+)[,\s]+(\d+)/.exec(c))) {
            return [+m[1], +m[2], +m[3]];
        }
        var named = {
            white: [255, 255, 255],
            black: [0, 0, 0],
            red: [255, 0, 0],
            blue: [0, 0, 255],
            green: [0, 128, 0],
            yellow: [255, 255, 0],
            gray: [128, 128, 128],
            grey: [128, 128, 128],
            silver: [192, 192, 192]
        };
        return named[c] || null;
    }

    // Light page colors fold into a short dark-gray ramp. Saturated blues become mid gray bars.
    function grayFor(rgb) {
        var y = (0.2126 * rgb[0] + 0.7152 * rgb[1] + 0.0722 * rgb[2]) / 255;
        var sat = (Math.max(rgb[0], rgb[1], rgb[2]) - Math.min(rgb[0], rgb[1], rgb[2])) / 255;
        if (y < 0.16 && sat < 0.25) return null;
        var out;
        if (y >= 0.94) out = 20;
        else if (y >= 0.82) out = 34;
        else if (y >= 0.62) out = 42;
        else out = 56;
        var h = out.toString(16);
        if (h.length < 2) h = '0' + h;
        return '#' + h + h + h;
    }

    function declaredBackground(el) {
        var attr = el.getAttribute && el.getAttribute('bgcolor');
        if (attr) return attr;
        var style = el.getAttribute && el.getAttribute('style');
        if (!style || style.indexOf('background') === -1) return null;
        var m = /background(?:-color)?\s*:\s*([^;]+)/i.exec(style);
        if (!m) return null;
        var v = m[1];
        var hex = /#(?:[0-9a-f]{3}|[0-9a-f]{6})\b/i.exec(v);
        if (hex) return hex[0];
        var named = /\b(white|black|red|blue|green|yellow|gray|grey|silver)\b/i.exec(v);
        return named ? named[1] : null;
    }

    function paint(el) {
        if (!el || el.nodeType !== 1 || el.id === 'if-dark-toggle') return;
        if (el.hasAttribute('data-if-painted')) return;
        var raw = declaredBackground(el);
        if (!raw) return;
        var rgb = parseColor(raw);
        if (!rgb) return;
        var gray = grayFor(rgb);
        if (!gray) return;
        el.setAttribute('data-if-prev-bg', el.style.getPropertyValue('background-color') || '');
        el.setAttribute('data-if-prev-pri', el.style.getPropertyPriority('background-color') || '');
        el.setAttribute('data-if-painted', '1');
        el.style.setProperty('background-color', gray, 'important');
    }

    function scan(root) {
        if (!root || !document.documentElement.classList.contains('if-dark')) return;
        if (root.nodeType === 1) paint(root);
        if (!root.querySelectorAll) return;
        var nodes = root.querySelectorAll('[bgcolor], [style*="background"]');
        for (var i = 0; i < nodes.length; i++) paint(nodes[i]);
    }

    function unpaint() {
        var nodes = document.querySelectorAll('[data-if-painted]');
        for (var i = 0; i < nodes.length; i++) {
            var el = nodes[i];
            var prev = el.getAttribute('data-if-prev-bg');
            var pri = el.getAttribute('data-if-prev-pri');
            if (prev) el.style.setProperty('background-color', prev, pri || '');
            else el.style.removeProperty('background-color');
            el.removeAttribute('data-if-prev-bg');
            el.removeAttribute('data-if-prev-pri');
            el.removeAttribute('data-if-painted');
        }
    }

    function updateButton() {
        var b = document.getElementById('if-dark-toggle');
        if (!b) return;
        var on = document.documentElement.classList.contains('if-dark');
        b.textContent = on ? '🌞' : '🌙';
        b.setAttribute('aria-pressed', on ? 'true' : 'false');
    }

    function mountToggle() {
        if (document.getElementById('if-dark-toggle') || !document.body) return;
        var b = document.createElement('button');
        b.id = 'if-dark-toggle';
        b.type = 'button';
        b.addEventListener('click', function (ev) {
            ev.preventDefault();
            ev.stopPropagation();
            var on = !document.documentElement.classList.contains('if-dark');
            setOn(on);
            applyRoot(on);
            if (on) scan(document);
            updateButton();
        }, true);
        document.body.appendChild(b);
        updateButton();
    }

    applyRoot(isOn());

    var style = document.createElement('style');
    style.id = 'if-dark-style';
    style.textContent = CSS;
    document.documentElement.appendChild(style);

    function boot() {
        mountToggle();
        if (document.documentElement.classList.contains('if-dark')) scan(document);
        if (window.MutationObserver && document.body) {
            var obs = new MutationObserver(function (muts) {
                if (!document.documentElement.classList.contains('if-dark')) return;
                for (var i = 0; i < muts.length; i++) {
                    var added = muts[i].addedNodes;
                    for (var j = 0; j < added.length; j++) {
                        var n = added[j];
                        if (n.nodeType === 1 && n.id !== 'if-dark-toggle') scan(n);
                    }
                }
            });
            obs.observe(document.body, { childList: true, subtree: true });
        }
    }

    if (document.readyState === 'loading') {
        document.addEventListener('DOMContentLoaded', boot);
    } else {
        boot();
    }
})();