Copy YouTube Transcript 3

Add a button to copy YouTube transcript to clipboard. Cần thêm điều kiện chỉ add nút ở trang phát video, thêm điều kiện đợi load transcript (nếu bấm được show thì đợi load), cần thêm điều kiện thoát khỏi lặp nếu như không tìm thấy transcript

За да инсталирате този скрипт, трябва да имате инсталирано разширение като Tampermonkey, Greasemonkey или Violentmonkey.

За да инсталирате този скрипт, трябва да инсталирате разширение, като например Tampermonkey .

За да инсталирате този скрипт, трябва да имате инсталирано разширение като Tampermonkey или Violentmonkey.

За да инсталирате този скрипт, трябва да имате инсталирано разширение като Tampermonkey или Userscripts.

За да инсталирате скрипта, трябва да инсталирате разширение като Tampermonkey.

За да инсталирате този скрипт, трябва да имате инсталиран скриптов мениджър.

(Вече имам скриптов мениджър, искам да го инсталирам!)

За да инсталирате този стил, трябва да инсталирате разширение като Stylus.

За да инсталирате този стил, трябва да инсталирате разширение като Stylus.

За да инсталирате този стил, трябва да инсталирате разширение като Stylus.

За да инсталирате този стил, трябва да имате инсталиран мениджър на потребителски стилове.

За да инсталирате този стил, трябва да имате инсталиран мениджър на потребителски стилове.

За да инсталирате този стил, трябва да имате инсталиран мениджър на потребителски стилове.

(Вече имам инсталиран мениджър на стиловете, искам да го инсталирам!)

// ==UserScript==
// @name         Copy YouTube Transcript 3
// @namespace    http://tampermonkey.net/
// @version      3
// @description  Add a button to copy YouTube transcript to clipboard. Cần thêm điều kiện chỉ add nút ở trang phát video, thêm điều kiện đợi load transcript (nếu bấm được show thì đợi load), cần thêm điều kiện thoát khỏi lặp nếu như không tìm thấy transcript
// @author       lmdw
// @match        https://www.youtube.com/*
// @grant        GM_setClipboard
// ==/UserScript==

(function () {
    'use strict';

    // Add button to the page
    function addButton() {
        // Check if the button already exists
        if (document.querySelector('#copy-transcript-button')) return;

        // Find the container for the button (below video player)
        const videoContainer = document.querySelector('#above-the-fold #title');

        if (!videoContainer) return;

        // Create the button
        const button = document.createElement('button');
        button.id = 'copy-transcript-button';
        button.textContent = 'Copy Transcript';
        button.className = 'yt-spec-button-shape-next yt-spec-button-shape-next--outline yt-spec-button-shape-next--call-to-action yt-spec-button-shape-next--size-m';
        button.style.marginTop = '8px'; // Add slight spacing

        // Append the button to the container
        videoContainer.parentNode.insertBefore(button, videoContainer.nextSibling);

        // Add click event to the button
        button.addEventListener('click', handleTranscriptCopy);
    }

    // Handle transcript copy process
    async function handleTranscriptCopy() {
        await clickExpandDescription();
        await clickShowTranscript();

        const transcript = getTranscript();

        if (!transcript || transcript.length === 0) {
            alert('No transcript available for this video.');
            return;
        }

        // Use GM_setClipboard to copy to clipboard
        GM_setClipboard(transcript);

        alert('Transcript copied to clipboard!');
    }

    // Click the "More" button to expand description
    async function clickExpandDescription() {
        const expandButton = document.querySelector('#expand');
        if (expandButton) {
            expandButton.click();
            await new Promise(resolve => setTimeout(resolve, 500)); // Wait for UI to update
        }
    }

    // Click the "Show Transcript" button
    async function clickShowTranscript() {
        const showTranscriptButton = document.querySelector("#primary-button > ytd-button-renderer > yt-button-shape > button");
        if (showTranscriptButton) {
            showTranscriptButton.click();
            await new Promise(resolve => setTimeout(resolve, 1000)); // Wait for transcript to load
        }
    }

    // Fetch transcript text
    function getTranscript() {
        // Find the container for transcript segments
        const transcriptContainer = document.querySelector('#segments-container');

        if (!transcriptContainer) {
            return null;
        }

        // Collect all transcript lines
        const lines = Array.from(
            transcriptContainer.querySelectorAll('.segment-text')
        );

        // Extract and join text content
        return lines.map(line => line.textContent.trim()).join('\n');
    }

    // Observe changes to the page and add button dynamically
    const observer = new MutationObserver(addButton);
    observer.observe(document.body, { childList: true, subtree: true });
})();