⚙️Coub Downloading

Add 3 Buttons to download Video,audio,loop when click button you can open it in new tab by click mouse button or right click selet open in new tab to preview.

当前为 2024-04-03 提交的版本,查看 最新版本

您需要先安装一个扩展,例如 篡改猴Greasemonkey暴力猴,之后才能安装此脚本。

您需要先安装一个扩展,例如 篡改猴暴力猴,之后才能安装此脚本。

您需要先安装一个扩展,例如 篡改猴暴力猴,之后才能安装此脚本。

您需要先安装一个扩展,例如 篡改猴Userscripts ,之后才能安装此脚本。

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey,才能安装此脚本。

您需要先安装用户脚本管理器扩展后才能安装此脚本。

(我已经安装了用户脚本管理器,让我安装!)

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

(我已经安装了用户样式管理器,让我安装!)

// ==UserScript==
// @name         ⚙️Coub Downloading
// @namespace    Wizzergod
// @version      1.0.1
// @description  Add 3 Buttons to download Video,audio,loop when click button you can open it in new tab by click mouse button or right click selet open in new tab to preview.
// @icon            https://www.google.com/s2/favicons?sz=64&domain=coub.com
// @author          Wizzergod
// @license         MIT
// @match        *://*.coub.com/*
// @match        *://coub.com/*
// @grant        none
// ==/UserScript==

(function () {
    'use strict';

    function addButton(container, text, url, download) {
        const button = document.createElement('a');
        button.innerText = text;
        button.classList.add('coubdl-button');
        button.href = url;
        if (download) {
            button.setAttribute('download', '');
            button.addEventListener('click', function(event) {
                event.preventDefault();
                downloadFile(url);
            });
        }
        container.appendChild(button);
    }

    function downloadFile(url) {
        const xhr = new XMLHttpRequest();
        xhr.open('GET', url, true);
        xhr.responseType = 'blob';
        xhr.onload = function() {
            const blob = xhr.response;
            const url = window.URL.createObjectURL(blob);
            const a = document.createElement('a');
            a.style.display = 'none';
            a.href = url;
            a.download = 'file';
            document.body.appendChild(a);
            a.click();
            window.URL.revokeObjectURL(url);
        };
        xhr.send(null);
    }

    function addControls() {
        const coubContainers = document.querySelectorAll('.coub');

        coubContainers.forEach(container => {
            const permalink = container.dataset.permalink;
            if (!permalink) {
                return;
            }

            const descriptionControls = container.querySelector('.description__controls');
            if (!descriptionControls) {
                return;
            }

            const existingControls = container.querySelector('.coubdl-button-group');
            if (existingControls) {
                return;
            }

            const controlsContainer = document.createElement('div');
            controlsContainer.classList.add('coubdl-button-group');

            const dataContainer = container.querySelector('.data script[type="text/json"]');
            if (dataContainer) {
                const data = JSON.parse(dataContainer.textContent);
                if (data && data.file_versions && data.file_versions.html5) {
                    const html5Data = data.file_versions.html5;

                    if (html5Data.video && html5Data.video.high && html5Data.video.high.url) {
                        const videoUrl = html5Data.video.high.url;
                        addButton(controlsContainer, 'Video', videoUrl, true);
                    }

                    if (html5Data.audio && html5Data.audio.high && html5Data.audio.high.url) {
                        const audioUrl = html5Data.audio.high.url;
                        addButton(controlsContainer, 'Audio', audioUrl, true);
                    }
                }

                if (data && data.file_versions && data.file_versions.share && data.file_versions.share.default) {
                    const loopedUrl = data.file_versions.share.default;
                    addButton(controlsContainer, 'Looped', loopedUrl, true);
                }
            }

            descriptionControls.prepend(controlsContainer);
        });
    }

    function observeChanges() {
        const observer = new MutationObserver(mutations => {
            mutations.forEach(mutation => {
                Array.from(mutation.addedNodes).forEach(node => {
                    if (node.nodeType === Node.ELEMENT_NODE) {
                        addControls();
                    }
                });
            });
        });

        observer.observe(document.body, {
            childList: true,
            subtree: true
        });
    }

    function init() {
        addControls();
        observeChanges();
    }

    // Add CSS styles
    const style = document.createElement('style');
    style.textContent = `
        .coubdl-button-group {
            display: inline-flex;
            white-space: nowrap;
            flex-wrap: nowrap;
            gap: 2px;
            margin-top: 1px;
            position: relative;
            right: 30%;
            top: 130%;
        }

        .coubdl-button {
            padding: 4px 8px;
            color: #fff;
            background: #000;
            line-height: 1;
            font-size: none;
            align-self: center;
            border-radius: 0px;
            position: absolute;
            text-decoration: none;
            border: none;
        }

        .coubdl-button:hover,
        .coubdl-button:active,
        .coubdl-button:focus {
            color: #e0e0e0;
        }
        .coubdl-button:nth-child(2) {
            left: 26px;
        }
        .coubdl-button:nth-child(3) {
            left: 80px;
        }
    `;
    document.head.appendChild(style);

    init();

})();