您需要先安装一个扩展,例如 篡改猴、Greasemonkey 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 Userscripts ,之后才能安装此脚本。
您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey,才能安装此脚本。
您需要先安装用户脚本管理器扩展后才能安装此脚本。
下载Pexels图片合集
// ==UserScript== // @name Pexels合集下载器 // @namespace Tampermonkey Scripts // @version 1.3 // @description 下载Pexels图片合集 // @author FOX // @match https://www.pexels.com/zh-cn/collections/* // @match https://www.pexels.com/collections/* // @grant GM_download // @license MIT // ==/UserScript== (function () { 'use strict'; let downloadedCount = 0; let totalImages = 0; let progressBarContainer, progressBarFill, progressText, progressTitle; let isDragging = false; let startOffsetX = 0; let startOffsetY = 0; function getCollectionTitle() { const collectionTitleElement = document.querySelector('.Text_text__D8yqX.Text_size-h60__tkvRy.Text_size-h28-mobile__p1MpK.Text_weight-semibold__GaFnn.Text_color-midnight2C343E__iCo4Q.spacing_noMargin__F5u9R.Text_center__q4tcr'); let collectionTitle = collectionTitleElement ? collectionTitleElement.textContent.trim() : 'Unknown_Collection'; // 替换掉文件名中不允许的字符 collectionTitle = collectionTitle.replace(/[\W_]+/g, "_"); return collectionTitle; } function updateProgressText() { if (progressText) { progressText.textContent = `当前进度:${downloadedCount}/${totalImages}`; progressBarFill.style.width = totalImages > 0 ? `${(downloadedCount / totalImages) * 100}%` : '0%'; // 更新进度条宽度 // 检查下载是否完成 if (downloadedCount >= totalImages) { // 设置2秒后自动关闭进度条 setTimeout(() => { if (progressBarContainer && progressBarContainer.parentNode) { progressBarContainer.parentNode.removeChild(progressBarContainer); } }, 2000); // 2秒后执行 } } } function downloadImage(url, name) { GM_download({ url: url, name: name, onerror: function (error) { console.error(`Download failed:`, error); downloadedCount++; updateProgressText(); }, ontimeout: function () { console.error(`Download timed out:`, url); downloadedCount++; updateProgressText(); }, onload: function () { downloadedCount++; updateProgressText(); } }); } function getImageUrls() { const downloadButtons = document.querySelectorAll('.Button_button__RDDf5.spacing_noMargin__F5u9R..spacing_pr20__ZH8T3..spacing_pl20__MrrA1.DownloadButton_downloadButton__0aNOo.DownloadButton_fullButtonOnDesktop__EWWUC.Button_clickable__DqoNe.Button_white__OVsmf.Link_link__Ime8c.spacing_noMargin__F5u9R'); totalImages = downloadButtons.length; return Array.from(downloadButtons).map(button => { const thumbUrl = button.getAttribute('href'); if (thumbUrl) { const photoIdMatch = thumbUrl.match(/photo-(\d+)/i); if (photoIdMatch && photoIdMatch[1]) { return `https://images.pexels.com/photos/${photoIdMatch[1]}/pexels-photo-${photoIdMatch[1]}.jpeg`; } } return null; }).filter(url => url !== null); } function startDownloadProcess() { // 确保所有图片加载完毕后再开始下载 autoScroll(() => { const imageUrls = getImageUrls(); totalImages = imageUrls.length; updateProgressText(); const collectionName = getCollectionTitle(); // 获取合集名称 imageUrls.forEach((url, index) => { // 包含合集名称在文件名中 setTimeout(() => downloadImage(url, `${collectionName}-${index + 1}.jpg`), index * 1000); }); }); } function autoScroll(callback) { const intervalDelay = 350; const pauseDuration = 2000; const scrollIncrement = 100; // 每次循环时增加的额外滚动量 let lastScrollHeight = 0; let sameScrollCounter = 0; // 计数器,用于跳过因内容加载导致的滚动高度不变 let incrementalScrollDistance = window.innerHeight; // 开始时等于一个窗口的高度 const scrollInterval = setInterval(() => { const currentScrollHeight = document.documentElement.scrollHeight; window.scrollBy(0, incrementalScrollDistance); if (currentScrollHeight === lastScrollHeight) { sameScrollCounter++; } else { sameScrollCounter = 0; // 如果检测到滚动高度改变,重置计数器 incrementalScrollDistance += scrollIncrement; // 增加滚动距离 } if (sameScrollCounter >= 3) { // 如果连续3次滚动高度未改变,则认为已到达底部 clearInterval(scrollInterval); setTimeout(() => { window.scrollTo(0, 0); // 返回顶部 if (typeof callback === "function") { callback(); } }, pauseDuration); } lastScrollHeight = currentScrollHeight; // 更新最后的滚动高度 }, intervalDelay); } // 添加下载按钮 function addProgressBar() { progressBarContainer = document.createElement('div'); Object.assign(progressBarContainer.style, { position: 'fixed', bottom: '50px', // 距离底部的像素 right: '5px', // 距离右侧的像素 backgroundColor: 'rgba(0,125,250,0.7)', // 0.7的半透明色 borderRadius: '10px', padding: '10px', width: '480px', // 进度条宽度 height: '65px', // 进度条高度 zIndex: '9999', boxShadow: '0 2px 4px rgba(0,0,0,0.2)', color: 'white', // 进度条文字颜色 fontFamily: 'Arial, sans-serif', fontSize: '13px', lineHeight: '1.4', cursor: 'move' // 添加拖动样式 }); progressTitle = document.createElement('div'); progressTitle.textContent = `正在下载合集:${getCollectionTitle()}`; progressBarContainer.appendChild(progressTitle); progressText = document.createElement('div'); progressText.textContent = '当前进度:0%'; progressBarContainer.appendChild(progressText); const progressBarBackground = document.createElement('div'); Object.assign(progressBarBackground.style, { width: '100%', backgroundColor: 'rgba(255,255,255,0.2)', //进度槽背景色 borderRadius: '5px', margin: '5px 0' }); progressBarContainer.appendChild(progressBarBackground); progressBarFill = document.createElement('div'); Object.assign(progressBarFill.style, { height: '5px', width: '0%', backgroundColor: '#1afff7', // 进度线条色 borderRadius: '5px', transition: 'width 0.5s ease-in-out' }); progressBarBackground.appendChild(progressBarFill); const movableText = document.createElement('div'); movableText.textContent = '(进度条可移动)'; Object.assign(movableText.style, { position: 'absolute', top: '4px', right: '4px', fontSize: '13px', padding: '5px', backgroundColor: 'rgba(0, 0, 0, 0)', color: 'white' }); progressBarContainer.appendChild(movableText); progressBarContainer.addEventListener('mousedown', startDragging); document.body.appendChild(progressBarContainer); } function startDragging(event) { isDragging = true; startOffsetX = event.clientX - progressBarContainer.offsetLeft; startOffsetY = event.clientY - progressBarContainer.offsetTop; document.addEventListener('mousemove', dragProgressBar); document.addEventListener('mouseup', stopDragging); } function dragProgressBar(event) { if (isDragging) { const offsetX = event.clientX - startOffsetX; const offsetY = event.clientY - startOffsetY; progressBarContainer.style.left = offsetX + 'px'; progressBarContainer.style.top = offsetY + 'px'; } } function stopDragging() { isDragging = false; document.removeEventListener('mousemove', dragProgressBar); document.removeEventListener('mouseup', stopDragging); } function addDownloadButton() { const userInfoElement = document.querySelector('.Page_users__MM9S2.Flex_flex__3z447.spacing_noMargin__F5u9R.spacing_mmb30__tk52K.spacing_tmb30__r_auH'); if (userInfoElement) { const downloadBtnContainer = document.createElement('div'); downloadBtnContainer.style.display = 'inline-flex'; downloadBtnContainer.style.alignItems = 'center'; downloadBtnContainer.style.marginLeft = '10px'; const downloadBtn = document.createElement('button'); downloadBtn.textContent = '下载合集'; downloadBtn.id = 'downloadBtn'; Object.assign(downloadBtn.style, { fontSize: '16px', color: 'white', background: '#05a081', border: 'none', borderRadius: '30px', height: '45px', width: '100px', cursor: 'pointer', padding: '8px 15px', margin: '0 10px' }); downloadBtnContainer.appendChild(downloadBtn); userInfoElement.parentNode.insertBefore(downloadBtnContainer, userInfoElement.nextSibling); downloadBtn.addEventListener('click', () => { addProgressBar(); startDownloadProcess(); }); } else { console.error('User information element not found.'); } } function checkAndInsertButton() { if (!document.getElementById('downloadBtn')) { addDownloadButton(); } } setInterval(checkAndInsertButton, 1000); })();