Google AI Studio - Enhanced Actions

Adds multi-select/delete (Checkbox, Ctrl+A, Shift+Click, Ctrl+Click, Delete key) and "Delete Thoughts" (Shift+F2) to Chat.

// ==UserScript==
// @name         Google AI Studio - Enhanced Actions
// @namespace    http://tampermonkey.net/
// @version      1.2
// @description  Adds multi-select/delete (Checkbox, Ctrl+A, Shift+Click, Ctrl+Click, Delete key) and "Delete Thoughts" (Shift+F2) to Chat.
// @author       User
// @match        https://aistudio.google.com/prompts/*
// @match        https://aistudio.google.com/library
// @icon         https://www.google.com/s2/favicons?sz=64&domain=google.com
// @grant        GM_addStyle
// @run-at       document-idle
// ==/UserScript==

(function() {
    'use strict';

    // --- Configuration & Constants ---
    const C = {
        CLASSES: {
            CHAT_CHECKBOX: 'gm-chat-select-checkbox',
            CHAT_SELECTED: 'gm-chat-selected',
            CHAT_DELETE_BEFORE: 'gm-chat-delete-before-item',
            LIB_CHECKBOX: 'gm-lib-select-checkbox',
            LIB_HEADER_CHECKBOX: 'gm-lib-header-select-checkbox',
            LIB_SELECTED: 'gm-lib-selected',
            LIB_CHECKBOX_CELL: 'gm-lib-checkbox-cell',
            LIB_CHECKBOX_HEADER: 'gm-lib-checkbox-header',
            ENABLED: 'enabled'
        },
        IDS: {
            CHAT_MULTI_DELETE_BTN: 'gm-chat-multi-delete-button',
            LIB_MULTI_DELETE_BTN: 'gm-lib-multi-delete-button'
        },
        SELECTORS: {
            CHAT_TURN: 'ms-chat-turn',
            CHAT_SESSION: 'ms-chat-session',
            CHAT_TURN_CONTAINER: '.chat-turn-container',
            CHAT_MORE_OPTIONS_BTN: 'ms-chat-turn-options button.mat-mdc-menu-trigger',
            CHAT_MORE_ACTIONS_BTN: 'button[aria-label="View more actions"]',
            MENU_PANEL: 'div.cdk-overlay-container div.mat-mdc-menu-panel',
            MENU_ITEM: 'button.mat-mdc-menu-item',
            OVERLAY_BACKDROP: 'div.cdk-overlay-backdrop',
            LIBRARY_TABLE: 'ms-library-table table.mat-mdc-table',
            LIBRARY_HEADER_ROW: 'thead tr.mat-mdc-header-row',
            LIBRARY_ROW: 'tbody tr.mat-mdc-row',
            LIBRARY_ACTIONS_WRAPPER: 'div.lib-header div.actions-wrapper',
            LIBRARY_MORE_OPTIONS_BTN: 'button[aria-label="Show overflow"]',
            DIALOG_CONTAINER: 'mat-dialog-container',
            DIALOG_ACTIONS: 'mat-dialog-actions button'
        },
        TIMEOUTS: {
            ELEMENT_WAIT: 5000,
            ELEMENT_DISAPPEAR: 5000,
            MENU_APPEAR_DELAY: 150
        }
    };

    // --- State Variables ---
    let selectedChatTurns = new Set();
    let selectedLibraryItems = new Set();
    let isDeleting = false;
    let lastClickedTurn = null;

    // --- Styles ---
    GM_addStyle(`
        ms-chat-turn .chat-turn-container { position: relative; padding-left: 35px !important; }
        .${C.CLASSES.CHAT_CHECKBOX} { position: absolute; left: 8px; top: 12px; z-index: 10; cursor: pointer; transform: scale(1.2); }
        ms-chat-turn.${C.CLASSES.CHAT_SELECTED} > div { background-color: rgba(0, 100, 255, 0.1) !important; border: 1px solid rgba(0, 100, 255, 0.3); border-radius: 8px; }
        #${C.IDS.CHAT_MULTI_DELETE_BTN} { margin-left: 10px; background-color: #dc3545; color: white; border: none; padding: 5px 10px; border-radius: 4px; font-size: 14px; opacity: 0.5; pointer-events: none; transition: opacity 0.2s; }
        #${C.IDS.CHAT_MULTI_DELETE_BTN}.${C.CLASSES.ENABLED} { opacity: 1; pointer-events: auto; cursor: pointer; }
        #${C.IDS.CHAT_MULTI_DELETE_BTN}:hover.${C.CLASSES.ENABLED} { background-color: #c82333; }
        #${C.IDS.CHAT_MULTI_DELETE_BTN}:disabled { background-color: #a0a0a0; cursor: not-allowed; }
        .${C.CLASSES.CHAT_DELETE_BEFORE} .mat-mdc-menu-item-text { display: flex; align-items: center; }
        .${C.CLASSES.CHAT_DELETE_BEFORE} .delete-before-marker { margin-right: 8px; font-weight: bold; }
        th.${C.CLASSES.LIB_CHECKBOX_HEADER}, td.${C.CLASSES.LIB_CHECKBOX_CELL} { width: 40px !important; padding: 0 8px 0 16px !important; }
        tr.${C.CLASSES.LIB_SELECTED} { background-color: rgba(0, 100, 255, 0.08) !important; }
        #${C.IDS.LIB_MULTI_DELETE_BTN} { margin-left: 8px; background-color: #dc3545; color: white; border: none; padding: 0 12px; height: 36px; line-height: 36px; border-radius: 18px; font-weight: 500; opacity: 0.5; pointer-events: none; transition: opacity 0.2s; display: inline-flex; align-items: center; }
        #${C.IDS.LIB_MULTI_DELETE_BTN} .material-symbols-outlined { font-size: 18px; margin-right: 6px; }
        #${C.IDS.LIB_MULTI_DELETE_BTN}.${C.CLASSES.ENABLED} { opacity: 1; pointer-events: auto; cursor: pointer; }
        #${C.IDS.LIB_MULTI_DELETE_BTN}:hover.${C.CLASSES.ENABLED} { background-color: #c82333; }
        #${C.IDS.LIB_MULTI_DELETE_BTN}:disabled { background-color: #cccccc; cursor: not-allowed; opacity: 0.6; }
    `);

    // --- Utility Functions ---
    function robustClick(element) {
        if (!element) return;
        const ownerDoc = element.ownerDocument;
        const ownerWindow = ownerDoc?.defaultView;
        if (!ownerWindow) return;
        ['pointerdown', 'mousedown', 'pointerup', 'mouseup', 'click'].forEach(type =>
            element.dispatchEvent(new ownerWindow.MouseEvent(type, { bubbles: true, cancelable: true, view: ownerWindow }))
        );
    }

    function waitForElement(selector, timeout = C.TIMEOUTS.ELEMENT_WAIT) {
        return new Promise((resolve, reject) => {
            let el = document.querySelector(selector);
            if (el) return resolve(el);
            const observer = new MutationObserver(() => {
                el = document.querySelector(selector);
                if (el) {
                    observer.disconnect();
                    resolve(el);
                }
            });
            observer.observe(document.body, { childList: true, subtree: true });
            setTimeout(() => {
                observer.disconnect();
                reject(new Error(`Element "${selector}" not found.`));
            }, timeout);
        });
    }

    function waitForElementToDisappear(element, timeout = C.TIMEOUTS.ELEMENT_DISAPPEAR) {
        return new Promise(resolve => {
            if (!element || !document.body.contains(element)) return resolve();
            const observer = new MutationObserver(() => {
                if (!document.body.contains(element)) {
                    observer.disconnect();
                    resolve();
                }
            });
            observer.observe(document.body, { childList: true, subtree: true });
            setTimeout(() => { observer.disconnect(); resolve(); }, timeout);
        });
    }

    async function withSuppressedConfirm(action) {
        const originalConfirm = window.confirm;
        window.confirm = () => true;
        try {
            await action();
        } finally {
            window.confirm = originalConfirm;
        }
    }

    // --- Chat View Functions ---
    function addChatCheckbox(turnElement) {
        if (turnElement.querySelector(`.${C.CLASSES.CHAT_CHECKBOX}`)) return;
        const checkbox = document.createElement('input');
        checkbox.type = 'checkbox';
        checkbox.className = C.CLASSES.CHAT_CHECKBOX;
        checkbox.title = 'Select this turn (Shift+Click for range, Ctrl+Click to multi-select)';
        const container = turnElement.querySelector(C.SELECTORS.CHAT_TURN_CONTAINER);
        container?.insertBefore(checkbox, container.firstChild);
    }

    function setupChatMoreOptionsListener(turnElement) {
        const moreOptionsButton = turnElement.querySelector(C.SELECTORS.CHAT_MORE_OPTIONS_BTN);
        if (!moreOptionsButton || moreOptionsButton.dataset.hasGmListener) return;
        moreOptionsButton.dataset.hasGmListener = 'true';
        moreOptionsButton.addEventListener('click', () => {
            if (isDeleting) return;
            setTimeout(() => {
                const menu = document.querySelector(C.SELECTORS.MENU_PANEL);
                if (menu) addChatDeleteBeforeMenuItem(menu, turnElement);
            }, C.TIMEOUTS.MENU_APPEAR_DELAY);
        });
    }

    function addChatDeleteBeforeMenuItem(menuPanel, targetTurnElement) {
        if (menuPanel.querySelector(`.${C.CLASSES.CHAT_DELETE_BEFORE}`)) return;
        const menuContent = menuPanel.querySelector('.mat-mdc-menu-content');
        if (!menuContent) return;
        const deleteItem = Array.from(menuPanel.querySelectorAll(C.SELECTORS.MENU_ITEM)).find(
            btn => btn.textContent.trim().toLowerCase() === 'delete'
        );
        const btn = document.createElement('button');
        btn.className = `mat-mdc-menu-item mat-focus-indicator ${C.CLASSES.CHAT_DELETE_BEFORE}`;
        btn.innerHTML = `<span class="mat-mdc-menu-item-text"><span class="delete-before-marker">[X]</span><span>Delete Before</span></span>`;
        btn.addEventListener('click', (e) => {
            e.stopPropagation();
            handleChatDeleteBefore(targetTurnElement);
        });
        if (deleteItem) menuContent.insertBefore(btn, deleteItem);
        else menuContent.appendChild(btn);
    }

    function handleChatClick(event) {
        const checkbox = event.target;
        if (!checkbox.matches(`.${C.CLASSES.CHAT_CHECKBOX}`)) return;
        const turnElement = checkbox.closest(C.SELECTORS.CHAT_TURN);
        if (!turnElement || isDeleting) {
            if (isDeleting) event.preventDefault();
            return;
        }
        if (lastClickedTurn && !document.body.contains(lastClickedTurn)) lastClickedTurn = null;
        const allTurns = Array.from(document.querySelectorAll(`${C.SELECTORS.CHAT_SESSION} ${C.SELECTORS.CHAT_TURN}`));
        if (event.shiftKey && lastClickedTurn) {
            const start = allTurns.indexOf(lastClickedTurn);
            const end = allTurns.indexOf(turnElement);
            if (start === -1 || end === -1) return;
            const range = allTurns.slice(Math.min(start, end), Math.max(start, end) + 1);
            if (!event.ctrlKey) deselectAllTurns(false);
            range.forEach(turn => selectTurn(turn, true));
        } else {
            const isSelected = selectedChatTurns.has(turnElement);
            if (!event.ctrlKey) {
                deselectAllTurns(false);
                if (!isSelected) selectTurn(turnElement, true);
            } else {
                selectTurn(turnElement, !isSelected);
            }
        }
        lastClickedTurn = turnElement;
        updateChatMultiDeleteButtonState();
    }

    function selectTurn(turnElement, shouldBeSelected) {
        const checkbox = turnElement.querySelector(`.${C.CLASSES.CHAT_CHECKBOX}`);
        if (shouldBeSelected) {
            selectedChatTurns.add(turnElement);
            turnElement.classList.add(C.CLASSES.CHAT_SELECTED);
            if (checkbox) checkbox.checked = true;
        } else {
            selectedChatTurns.delete(turnElement);
            turnElement.classList.remove(C.CLASSES.CHAT_SELECTED);
            if (checkbox) checkbox.checked = false;
        }
    }

    function deselectAllTurns(updateButtonState = true) {
        selectedChatTurns.forEach(turn => selectTurn(turn, false));
        selectedChatTurns.clear();
        if (updateButtonState) updateChatMultiDeleteButtonState();
    }

    async function deleteSingleChatTurn(turnElement) {
        const moreOptionsButton = turnElement.querySelector(C.SELECTORS.CHAT_MORE_OPTIONS_BTN);
        if (!moreOptionsButton) return false;
        robustClick(moreOptionsButton);
        try {
            const menu = await waitForElement(`${C.SELECTORS.MENU_PANEL}:has(${C.SELECTORS.MENU_ITEM})`);
            const deleteButton = Array.from(menu.querySelectorAll(C.SELECTORS.MENU_ITEM)).find(btn => {
                const text = btn.textContent.trim().toLowerCase();
                return text.includes('delete') && !text.includes('before');
            });
            if (deleteButton) {
                robustClick(deleteButton);
                await waitForElementToDisappear(turnElement);
                return true;
            }
            return false;
        } catch (error) {
            const backdrop = document.querySelector(C.SELECTORS.OVERLAY_BACKDROP);
            if (backdrop) robustClick(backdrop);
            return false;
        }
    }

    async function performChatDeletion(turnsToDelete) {
        if (isDeleting || turnsToDelete.length === 0) return;
        const turnsArray = [...turnsToDelete].sort((a, b) => b.compareDocumentPosition(a) & Node.DOCUMENT_POSITION_FOLLOWING ? 1 : -1);
        await withSuppressedConfirm(async () => {
            isDeleting = true;
            updateChatMultiDeleteButtonState();
            try {
                for (const turn of turnsArray) {
                    if (document.body.contains(turn)) await deleteSingleChatTurn(turn);
                }
            } finally {
                isDeleting = false;
                updateChatMultiDeleteButtonState();
            }
        });
    }

    async function handleChatDeleteSelected() {
        const turnsToDelete = [...selectedChatTurns];
        if (turnsToDelete.length === 0) return;
        deselectAllTurns(false);
        await performChatDeletion(turnsToDelete);
    }

    async function handleChatDeleteBefore(targetTurnElement) {
        if (!targetTurnElement?.isConnected) return;
        const allTurns = Array.from(document.querySelectorAll(`${C.SELECTORS.CHAT_SESSION} ${C.SELECTORS.CHAT_TURN}`));
        const idx = allTurns.indexOf(targetTurnElement);
        if (idx <= 0) return;
        const turnsToDelete = allTurns.slice(0, idx);
        if (turnsToDelete.length > 0) {
            deselectAllTurns(false);
            await performChatDeletion(turnsToDelete);
        }
    }

    async function handleDeleteThoughts() {
        const thoughtTurns = Array.from(document.querySelectorAll(C.SELECTORS.CHAT_TURN)).filter(turn =>
            turn.querySelector('mat-expansion-panel-header')?.textContent.trim().startsWith('Thoughts')
        );
        if (thoughtTurns.length > 0) await performChatDeletion(thoughtTurns);
    }

    function addChatMultiDeleteButton() {
        if (document.getElementById(C.IDS.CHAT_MULTI_DELETE_BTN)) return;
        const moreButton = document.querySelector(C.SELECTORS.CHAT_MORE_ACTIONS_BTN);
        if (!moreButton?.parentElement) return;
        const btn = document.createElement('button');
        btn.id = C.IDS.CHAT_MULTI_DELETE_BTN;
        btn.addEventListener('click', handleChatDeleteSelected);
        moreButton.parentElement.insertBefore(btn, moreButton);
        updateChatMultiDeleteButtonState();
    }

    function updateChatMultiDeleteButtonState() {
        const btn = document.getElementById(C.IDS.CHAT_MULTI_DELETE_BTN);
        if (!btn) return;
        const count = selectedChatTurns.size;
        btn.textContent = isDeleting ? 'Deleting...' : `Delete Selected (${count})`;
        const enabled = count > 0 && !isDeleting;
        btn.classList.toggle(C.CLASSES.ENABLED, enabled);
        btn.disabled = !enabled;
    }

    function observeChatArea() {
        const container = document.querySelector(C.SELECTORS.CHAT_SESSION);
        if (!container) return;
        container.addEventListener('click', handleChatClick);
        document.querySelectorAll(`${C.SELECTORS.CHAT_SESSION} ${C.SELECTORS.CHAT_TURN}`).forEach(turn => {
            addChatCheckbox(turn);
            setupChatMoreOptionsListener(turn);
        });
        addChatMultiDeleteButton();
        const observer = new MutationObserver(mutations => {
            for (const m of mutations) {
                m.addedNodes.forEach(n => {
                    if (n.nodeType === Node.ELEMENT_NODE) {
                        const turns = n.matches(C.SELECTORS.CHAT_TURN) ? [n] : n.querySelectorAll(C.SELECTORS.CHAT_TURN);
                        turns.forEach(turn => {
                            addChatCheckbox(turn);
                            setupChatMoreOptionsListener(turn);
                        });
                    }
                });
                m.removedNodes.forEach(n => {
                    if (n.nodeType === Node.ELEMENT_NODE && selectedChatTurns.has(n)) {
                        selectedChatTurns.delete(n);
                        updateChatMultiDeleteButtonState();
                    }
                });
            }
        });
        observer.observe(container, { childList: true, subtree: true });
    }

    // --- Library View Functions ---
    function addLibraryCheckbox(rowElement) {
        if (rowElement.querySelector(`.${C.CLASSES.LIB_CHECKBOX_CELL}`)) return;
        const cell = document.createElement('td');
        cell.className = `mat-mdc-cell mdc-data-table__cell cdk-cell ${C.CLASSES.LIB_CHECKBOX_CELL}`;
        cell.innerHTML = `<input type="checkbox" class="${C.CLASSES.LIB_CHECKBOX}">`;
        rowElement.insertBefore(cell, rowElement.firstChild);
    }

    function addLibraryHeaderCheckbox(headerRow) {
        if (headerRow.querySelector(`.${C.CLASSES.LIB_CHECKBOX_HEADER}`)) return;
        const headerCell = document.createElement('th');
        headerCell.className = `mat-mdc-header-cell mdc-data-table__header-cell cdk-header-cell ${C.CLASSES.LIB_CHECKBOX_HEADER}`;
        headerCell.innerHTML = `<input type="checkbox" class="${C.CLASSES.LIB_HEADER_CHECKBOX}" title="Select/Deselect All Visible">`;
        headerRow.insertBefore(headerCell, headerRow.firstChild);
    }

    function handleLibraryClick(event) {
        const target = event.target;
        if (target.matches(`.${C.CLASSES.LIB_HEADER_CHECKBOX}`)) {
            const isChecked = target.checked;
            document.querySelectorAll(C.SELECTORS.LIBRARY_ROW).forEach(row => {
                const rowCheckbox = row.querySelector(`input.${C.CLASSES.LIB_CHECKBOX}`);
                if (rowCheckbox) rowCheckbox.checked = isChecked;
                row.classList.toggle(C.CLASSES.LIB_SELECTED, isChecked);
                if (isChecked) selectedLibraryItems.add(row);
                else selectedLibraryItems.delete(row);
            });
        } else if (target.matches(`.${C.CLASSES.LIB_CHECKBOX}`)) {
            const row = target.closest('tr');
            if (row) {
                row.classList.toggle(C.CLASSES.LIB_SELECTED, target.checked);
                if (target.checked) selectedLibraryItems.add(row);
                else selectedLibraryItems.delete(row);
            }
        }
        updateLibraryMultiDeleteButtonState();
    }

    function addLibraryMultiDeleteButton() {
        if (document.getElementById(C.IDS.LIB_MULTI_DELETE_BTN)) return;
        const actionsWrapper = document.querySelector(C.SELECTORS.LIBRARY_ACTIONS_WRAPPER);
        if (!actionsWrapper) return;
        const button = document.createElement('button');
        button.id = C.IDS.LIB_MULTI_DELETE_BTN;
        button.innerHTML = `<span class="material-symbols-outlined">delete</span><span class="button-text">Delete Selected (0)</span>`;
        button.addEventListener('click', handleLibraryDeleteSelected);
        actionsWrapper.appendChild(button);
        updateLibraryMultiDeleteButtonState();
    }

    function updateLibraryMultiDeleteButtonState() {
        const button = document.getElementById(C.IDS.LIB_MULTI_DELETE_BTN);
        if (!button) return;
        const count = selectedLibraryItems.size;
        button.querySelector('.button-text').textContent = `Delete Selected (${count})`;
        const enabled = count > 0 && !isDeleting;
        button.classList.toggle(C.CLASSES.ENABLED, enabled);
        button.disabled = !enabled;
    }

    async function deleteSingleLibraryItem(rowElement) {
        const moreOptionsButton = rowElement.querySelector(C.SELECTORS.LIBRARY_MORE_OPTIONS_BTN);
        if (!moreOptionsButton) return false;
        robustClick(moreOptionsButton);
        try {
            const menu = await waitForElement(`${C.SELECTORS.MENU_PANEL}:has(${C.SELECTORS.MENU_ITEM})`);
            const deletePromptButton = Array.from(menu.querySelectorAll(C.SELECTORS.MENU_ITEM)).find(
                btn => btn.textContent.trim().toLowerCase().includes('delete prompt')
            );
            if (!deletePromptButton) return false;
            robustClick(deletePromptButton);
            const dialog = await waitForElement(C.SELECTORS.DIALOG_CONTAINER);
            const finalDeleteButton = Array.from(dialog.querySelectorAll(C.SELECTORS.DIALOG_ACTIONS)).find(
                btn => btn.textContent.trim().toLowerCase() === 'delete'
            );
            if (!finalDeleteButton) return false;
            robustClick(finalDeleteButton);
            await waitForElementToDisappear(rowElement);
            return true;
        } catch (error) {
            const backdrop = document.querySelector(C.SELECTORS.OVERLAY_BACKDROP);
            if (backdrop) robustClick(backdrop);
            return false;
        }
    }

    async function handleLibraryDeleteSelected() {
        if (isDeleting || selectedLibraryItems.size === 0) return;
        await withSuppressedConfirm(async () => {
            isDeleting = true;
            updateLibraryMultiDeleteButtonState();
            try {
                const itemsToDelete = [...selectedLibraryItems];
                selectedLibraryItems.clear();
                for (const row of itemsToDelete) {
                    if (row.isConnected) await deleteSingleLibraryItem(row);
                }
            } finally {
                isDeleting = false;
                updateLibraryMultiDeleteButtonState();
            }
        });
    }

    function observeLibraryTable() {
        const table = document.querySelector(C.SELECTORS.LIBRARY_TABLE);
        if (!table) return;
        table.addEventListener('click', handleLibraryClick);
        const headerRow = table.querySelector(C.SELECTORS.LIBRARY_HEADER_ROW);
        if (headerRow) addLibraryHeaderCheckbox(headerRow);
        table.querySelectorAll(C.SELECTORS.LIBRARY_ROW).forEach(addLibraryCheckbox);
        addLibraryMultiDeleteButton();
        const observer = new MutationObserver(() => {
            table.querySelectorAll(`${C.SELECTORS.LIBRARY_ROW}:not(:has(.${C.CLASSES.LIB_CHECKBOX_CELL}))`).forEach(addLibraryCheckbox);
        });
        const tbody = table.querySelector('tbody');
        if (tbody) observer.observe(tbody, { childList: true });
    }

    // --- Global Listeners & Initialization ---
    function setupGlobalListeners() {
        document.addEventListener('keydown', (event) => {
            const activeEl = document.activeElement;
            const isTyping = activeEl && (activeEl.tagName === 'TEXTAREA' || activeEl.isContentEditable || (activeEl.tagName === 'INPUT' && /^(text|search|password|tel|url)$/i.test(activeEl.type)));
            if (isTyping || isDeleting) return;

            if (window.location.pathname.startsWith('/prompts/')) {
                if (event.ctrlKey && event.key.toLowerCase() === 'a') {
                    event.preventDefault();
                    const allTurns = document.querySelectorAll(`${C.SELECTORS.CHAT_SESSION} ${C.SELECTORS.CHAT_TURN}`);
                    const allSelected = selectedChatTurns.size === allTurns.length && allTurns.length > 0;
                    deselectAllTurns(false);
                    if (!allSelected) allTurns.forEach(turn => selectTurn(turn, true));
                    updateChatMultiDeleteButtonState();
                } else if (event.key === 'Escape') {
                    if (selectedChatTurns.size > 0) {
                        event.preventDefault();
                        deselectAllTurns();
                        lastClickedTurn = null;
                    }
                } else if (event.key === 'Delete') {
                    if (selectedChatTurns.size > 0) {
                        event.preventDefault();
                        document.getElementById(C.IDS.CHAT_MULTI_DELETE_BTN)?.click();
                    }
                } else if (event.shiftKey && event.key === 'F2') {
                    event.preventDefault();
                    handleDeleteThoughts();
                }
            }
        });

        document.addEventListener('click', (event) => {
            if (window.location.pathname.startsWith('/prompts/') && selectedChatTurns.size > 0 && !event.target.closest(`${C.SELECTORS.CHAT_TURN}, #${C.IDS.CHAT_MULTI_DELETE_BTN}`)) {
                deselectAllTurns();
                lastClickedTurn = null;
            }
        });
    }

    async function initialize() {
        const currentPath = window.location.pathname;
        try {
            if (currentPath.startsWith('/prompts/')) {
                await waitForElement(C.SELECTORS.CHAT_SESSION);
                observeChatArea();
            } else if (currentPath === '/library') {
                await waitForElement(C.SELECTORS.LIBRARY_TABLE);
                observeLibraryTable();
            }
            setupGlobalListeners();
        } catch (error) {
            console.error('[Enhanced Actions] Initialization failed:', error);
        }
    }

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