| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176 |
- // 复制按钮功能
- window.setupCopyButtons = function () {
- // 复制图标SVG
- const copySvg = `<svg xmlns="http://www.w3.org/2000/svg" width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
- <rect x="9" y="9" width="13" height="13" rx="2" ry="2"></rect>
- <path d="M5 15H4a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h9a2 2 0 0 1 2 2v1"></path>
- </svg>`;
- // 为所有消息添加复制按钮
- function addCopyButtonsToMessages () {
- const messages = document.querySelectorAll('.message');
- messages.forEach(message => {
- // 如果消息已经有复制按钮,则跳过
- if (message.querySelector('.copy-button')) return;
- const messageContent = message.querySelector('.message-content');
- if (!messageContent) return;
- // 创建复制按钮
- const copyButton = document.createElement('button');
- copyButton.className = 'copy-button';
- copyButton.innerHTML = copySvg;
- copyButton.setAttribute('aria-label', '复制内容');
- copyButton.title = '复制消息内容';
- // 添加点击事件
- copyButton.addEventListener('click', (e) => {
- e.stopPropagation(); // 阻止事件冒泡
- copyMessageContent(messageContent);
- });
- // 添加到消息元素中,与message-content同级
- message.appendChild(copyButton);
- });
- }
- // 复制消息内容
- function copyMessageContent (messageContent) {
- try {
- // 获取纯文本内容
- const textContent = messageContent.textContent;
- // 检查是否支持现代剪贴板API
- if (navigator.clipboard && navigator.clipboard.writeText) {
- // 使用现代剪贴板API
- navigator.clipboard.writeText(textContent)
- .then(() => {
- showNotification('复制成功!', 'success');
- })
- .catch(err => {
- console.error('现代剪贴板API复制失败:', err);
- // 回退到传统方法
- fallbackCopyTextToClipboard(textContent);
- });
- } else {
- // 回退到传统方法
- fallbackCopyTextToClipboard(textContent);
- }
- } catch (err) {
- console.error('复制过程中出错:', err);
- // 回退到传统方法
- fallbackCopyTextToClipboard(messageContent.textContent);
- }
- }
- // 传统复制方法(兼容性更好)
- function fallbackCopyTextToClipboard (text) {
- try {
- // 创建临时文本区域
- const textArea = document.createElement('textarea');
- textArea.value = text;
- // 设置样式使其不可见
- textArea.style.position = 'fixed';
- textArea.style.top = '0';
- textArea.style.left = '0';
- textArea.style.width = '2em';
- textArea.style.height = '2em';
- textArea.style.padding = '0';
- textArea.style.border = 'none';
- textArea.style.outline = 'none';
- textArea.style.boxShadow = 'none';
- textArea.style.background = 'transparent';
- textArea.style.opacity = '0';
- textArea.style.zIndex = '-1';
- // 添加到页面
- document.body.appendChild(textArea);
- // 选中文本
- textArea.focus();
- textArea.select();
- // 尝试复制
- const successful = document.execCommand('copy');
- // 移除临时元素
- document.body.removeChild(textArea);
- if (successful) {
- showNotification('复制成功!', 'success');
- } else {
- showNotification('复制失败,请手动选择文本复制', 'error');
- }
- } catch (err) {
- console.error('传统复制方法也失败:', err);
- showNotification('复制失败,请手动选择文本复制', 'error');
- }
- }
- // 显示通知
- function showNotification (message, type) {
- // 移除之前的通知
- const existingNotification = document.querySelector('.copy-notification');
- if (existingNotification) {
- existingNotification.remove();
- }
- // 创建通知元素
- const notification = document.createElement('div');
- notification.className = `copy-notification ${type}`;
- notification.textContent = message;
- // 将通知定位到页面中央
- notification.style.top = '50%';
- notification.style.left = '50%';
- notification.style.right = 'auto';
- notification.style.transform = 'translate(-50%, -50%)';
- // 添加到文档
- document.body.appendChild(notification);
- // 显示通知
- setTimeout(() => {
- notification.classList.add('show');
- }, 10);
- // 0.5秒后隐藏并移除通知
- setTimeout(() => {
- notification.classList.remove('show');
- // 等待过渡动画完成后移除元素
- setTimeout(() => {
- if (notification.parentNode) {
- notification.parentNode.removeChild(notification);
- }
- }, 300);
- }, 500);
- }
- // 初始调用一次,添加现有消息的复制按钮
- addCopyButtonsToMessages();
- // 创建观察器监听DOM变化,为新添加的消息添加复制按钮
- const observer = new MutationObserver((mutations) => {
- mutations.forEach((mutation) => {
- if (mutation.addedNodes.length) {
- addCopyButtonsToMessages();
- }
- });
- });
- // 开始观察聊天容器
- const chatMessages = document.getElementById('chat-messages');
- if (chatMessages) {
- observer.observe(chatMessages, { childList: true, subtree: true });
- }
- };
- // 页面加载完成后自动执行
- document.addEventListener('DOMContentLoaded', () => {
- if (typeof window.setupCopyButtons === 'function') {
- window.setupCopyButtons();
- }
- });
|