From b3ae78c75a3de1bdfed8f9d7488993e29f52be25 Mon Sep 17 00:00:00 2001
From: MaJiangla <2652352927@qq.com>
Date: Fri, 13 Feb 2026 20:55:08 +0800
Subject: [PATCH 1/2] =?UTF-8?q?=E6=9B=B4=E6=96=B0=E4=B8=AD=E5=9B=BD?=
=?UTF-8?q?=E7=89=88=E5=A3=81=E7=BA=B8API=E5=B9=B6=E8=AE=BE=E7=BD=AE?=
=?UTF-8?q?=E5=88=9D=E5=A7=8B=E5=8C=96=E4=BB=8A=E6=97=A5=E5=A3=81=E7=BA=B8?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
README.md | 135 ++++++++++++++++++++-----------------
script.js | 184 +++++++++++++++++++++++++--------------------------
wallpaper.js | 124 +++++++++++++++++-----------------
3 files changed, 230 insertions(+), 213 deletions(-)
diff --git a/README.md b/README.md
index de8c3ed..cd72333 100644
--- a/README.md
+++ b/README.md
@@ -1,60 +1,75 @@
-# RandomWord - 英语单词动态壁纸
-
-[](LICENSE)
-[](https://github.com/rocksdanister/lively)
-[](https://github.com/kajweb/dict)
-
-在精美壁纸上学习英语单词的动态壁纸应用,支持 Lively Wallpaper。
-
-[在线预览](https://majiangla.github.io/RandomWord/)
-
-## ✨ 功能特色
-
-- 📚 内置高中/四级词库,支持自定义 CSV 导入
-- 🎨 智能主题色提取,从壁纸自动配色
-- 📍 可调卡片位置(横纵百分比)
-- 🔄 自动切换单词和壁纸
-- 🌄 必应每日壁纸(国际版/中国版双源)
-
-## 🚀 快速使用
-
-**本地运行:**
-```bash
-git clone https://github.com/majiangla/RandomWord.git
-cd RandomWord
-python -m http.server 8000
-```
-访问 `http://localhost:8000`
-
-**Lively 壁纸:**
-1. [下载 Release](https://github.com/majiangla/RandomWord/releases/tag/pnblish)
-2. 拖入 Lively Wallpaper 窗口
-
-## ⚙️ 基本设置
-
-1. **词书选择**:高中/四级或自定义 CSV
-2. **位置调整**:水平/垂直滑块 (0-100%)
-3. **显示控制**:单词/释义开关,动画开关
-4. **自动模式**:设置切换间隔时间
-
-## 📄 词书格式
-
-```csv
-单词,释义
-apple,苹果
-book,书
-computer,计算机
-```
-
-## 🤝 致谢
-
-- [bing-wallpaper](https://github.com/niumoo/bing-wallpaper) - 壁纸数据
-- [dict](https://github.com/kajweb/dict) - 词典数据
-
-## 📄 许可证
-
-AGPL-3.0 © [MaJiang](https://github.com/majiangla)
-
----
-
-⭐ **欢迎 Star 和 Fork!**
+# RandomWord - 英语单词动态壁纸
+
+[](LICENSE)
+[](https://github.com/rocksdanister/lively)
+[](https://github.com/kajweb/dict)
+
+在精美壁纸上学习英语单词的动态壁纸应用,支持 Lively Wallpaper。
+
+[在线预览](https://majiangla.github.io/RandomWord/)
+
+## ✨ 功能特色
+
+- 📚 内置高中/四级词库,支持自定义 CSV 导入
+- 🎨 智能主题色提取,从壁纸自动配色
+- 📍 可调卡片位置(横纵百分比)
+- 🔄 自动切换单词和壁纸
+- 🌄 必应每日壁纸(中国版新 API + 国际版 GitHub 数据)
+
+## 🚀 快速使用
+
+**本地运行:**
+```bash
+git clone https://github.com/majiangla/RandomWord.git
+cd RandomWord
+python -m http.server 8000
+```
+访问 `http://localhost:8000`
+
+**Lively 壁纸:**
+1. [下载 Release](https://github.com/majiangla/RandomWord/releases/tag/pnblish)
+2. 拖入 Lively Wallpaper 窗口
+
+## ⚙️ 基本设置
+
+1. **词书选择**:高中/四级或自定义 CSV
+2. **位置调整**:水平/垂直滑块 (0-100%)
+3. **显示控制**:单词/释义开关,动画开关
+4. **自动模式**:设置切换间隔时间
+
+
+## 🖼️ 中国版 Bing 壁纸开放 API
+
+本站中国版壁纸使用以下可直接引用的图片 API:
+
+- 今日壁纸(长期服务):`https://bing.img.run/uhd.php`
+- 随机历史壁纸:`https://bing.img.run/rand_uhd.php`(收录范围:2020-09-01 至今)
+
+可直接作为 `img` 链接使用:
+
+```html
+
+
+```
+
+## 📄 词书格式
+
+```csv
+单词,释义
+apple,苹果
+book,书
+computer,计算机
+```
+
+## 🤝 致谢
+
+- [bing-wallpaper](https://github.com/niumoo/bing-wallpaper) - 壁纸数据
+- [dict](https://github.com/kajweb/dict) - 词典数据
+
+## 📄 许可证
+
+AGPL-3.0 © [MaJiang](https://github.com/majiangla)
+
+---
+
+⭐ **欢迎 Star 和 Fork!**
diff --git a/script.js b/script.js
index 30fff92..ea61b7e 100644
--- a/script.js
+++ b/script.js
@@ -1,93 +1,93 @@
-// 主应用程序
-class VocabularyApp {
- constructor() {
- // 初始化模块
- this.wordManager = new WordManager();
- this.wallpaperManager = new WallpaperManager();
- this.settingsManager = new SettingsManager(this.wordManager, this.wallpaperManager);
-
- // 全局状态
- this.isInitialized = false;
- }
-
- // 初始化应用程序
- async init() {
- if (this.isInitialized) return;
-
- // 显示启动信息
- this.showWelcomeMessage();
-
- // 初始化UI
- this.settingsManager.initUIElements();
-
- // 尝试自动加载词书
- const hasWords = await this.wordManager.tryAutoLoad();
-
- // 显示随机单词
- this.showRandomWord();
-
- // 设置壁纸
- this.wallpaperManager.setRandomBingBackground();
-
- // 设置全局事件监听
- this.setupGlobalEventListeners();
-
- this.isInitialized = true;
- Logger.log('应用程序初始化完成');
- }
-
- // 显示欢迎信息
- showWelcomeMessage() {
- console.log('====================================');
- console.log('MaJiang - 英语单词随机展示系统');
- console.log('作者: MaJiangla (Bilibili: 1431497051)');
- console.log('功能说明:');
- console.log(' • 点击页面任意位置切换单词');
- console.log(' • 每 ' + this.settingsManager.settings.bgInterval + ' 个单词切换一次壁纸');
- console.log(' • 支持导入CSV格式单词表');
- console.log(' • 支持自动模式');
- console.log(' • 支持词书选择');
- console.log('====================================');
- }
-
- // 设置全局事件监听器
- setupGlobalEventListeners() {
- // 点击页面切换单词
- document.body.addEventListener('click', (e) => {
- if (!this.settingsManager.elements.settingsMenu.contains(e.target) &&
- !this.settingsManager.elements.settingsBtn.contains(e.target)) {
- this.showRandomWord();
- }
- });
- }
-
- // 显示随机单词
- showRandomWord() {
- const entry = this.wordManager.showRandom();
-
- // 更新显示
- this.settingsManager.updateDisplay(entry.word, entry.meaning);
-
- // 记录日志
- Logger.logWord(entry.word, entry.meaning ? entry.meaning.replace(/\n/g, ' ') : '(无释义)');
-
- // 增加点击计数
- this.settingsManager.incrementClickCount();
- }
-}
-
-// 创建全局实例
-let app;
-
-// 将showRandomWord暴露为全局函数(提前定义,避免空闲检测时未定义)
-window.showRandomWord = () => {
- if (app && typeof app.showRandomWord === 'function') {
- app.showRandomWord();
- }
-};
-
-// 页面加载完成后初始化
-window.onload = async function() {
- app = new VocabularyApp();
- await app.init();
+// 主应用程序
+class VocabularyApp {
+ constructor() {
+ // 初始化模块
+ this.wordManager = new WordManager();
+ this.wallpaperManager = new WallpaperManager();
+ this.settingsManager = new SettingsManager(this.wordManager, this.wallpaperManager);
+
+ // 全局状态
+ this.isInitialized = false;
+ }
+
+ // 初始化应用程序
+ async init() {
+ if (this.isInitialized) return;
+
+ // 显示启动信息
+ this.showWelcomeMessage();
+
+ // 初始化UI
+ this.settingsManager.initUIElements();
+
+ // 尝试自动加载词书
+ const hasWords = await this.wordManager.tryAutoLoad();
+
+ // 显示随机单词
+ this.showRandomWord();
+
+ // 设置壁纸(初始化固定为中国版必应今日壁纸)
+ this.wallpaperManager.setChineseDailyBackground();
+
+ // 设置全局事件监听
+ this.setupGlobalEventListeners();
+
+ this.isInitialized = true;
+ Logger.log('应用程序初始化完成');
+ }
+
+ // 显示欢迎信息
+ showWelcomeMessage() {
+ console.log('====================================');
+ console.log('MaJiang - 英语单词随机展示系统');
+ console.log('作者: MaJiangla (Bilibili: 1431497051)');
+ console.log('功能说明:');
+ console.log(' • 点击页面任意位置切换单词');
+ console.log(' • 每 ' + this.settingsManager.settings.bgInterval + ' 个单词切换一次壁纸');
+ console.log(' • 支持导入CSV格式单词表');
+ console.log(' • 支持自动模式');
+ console.log(' • 支持词书选择');
+ console.log('====================================');
+ }
+
+ // 设置全局事件监听器
+ setupGlobalEventListeners() {
+ // 点击页面切换单词
+ document.body.addEventListener('click', (e) => {
+ if (!this.settingsManager.elements.settingsMenu.contains(e.target) &&
+ !this.settingsManager.elements.settingsBtn.contains(e.target)) {
+ this.showRandomWord();
+ }
+ });
+ }
+
+ // 显示随机单词
+ showRandomWord() {
+ const entry = this.wordManager.showRandom();
+
+ // 更新显示
+ this.settingsManager.updateDisplay(entry.word, entry.meaning);
+
+ // 记录日志
+ Logger.logWord(entry.word, entry.meaning ? entry.meaning.replace(/\n/g, ' ') : '(无释义)');
+
+ // 增加点击计数
+ this.settingsManager.incrementClickCount();
+ }
+}
+
+// 创建全局实例
+let app;
+
+// 将showRandomWord暴露为全局函数(提前定义,避免空闲检测时未定义)
+window.showRandomWord = () => {
+ if (app && typeof app.showRandomWord === 'function') {
+ app.showRandomWord();
+ }
+};
+
+// 页面加载完成后初始化
+window.onload = async function() {
+ app = new VocabularyApp();
+ await app.init();
};
\ No newline at end of file
diff --git a/wallpaper.js b/wallpaper.js
index b144f07..5aeb411 100644
--- a/wallpaper.js
+++ b/wallpaper.js
@@ -1,11 +1,49 @@
// 壁纸管理模块
class WallpaperManager {
- constructor() {
- this.currentWallpaperUrl = '';
- this.currentThemeColor = CONSTANTS.DEFAULT_THEME_COLOR;
- this.isChangingBg = false;
- this.wallPaperSources = JSON.parse(JSON.stringify(CONSTANTS.WALLPAPER_SOURCES));
- }
+ constructor() {
+ this.currentWallpaperUrl = '';
+ this.currentWallpaperApiUrl = '';
+ this.currentThemeColor = CONSTANTS.DEFAULT_THEME_COLOR;
+ this.isChangingBg = false;
+ this.wallPaperSources = JSON.parse(JSON.stringify(CONSTANTS.WALLPAPER_SOURCES));
+ }
+
+ // 设置中国版今日壁纸(初始化用)
+ setChineseDailyBackground() {
+ const dailyWallpaperUrl = 'https://bing.img.run/uhd.php';
+ this.currentWallpaperApiUrl = dailyWallpaperUrl;
+ this.loadAndApplyWallpaper(dailyWallpaperUrl, dailyWallpaperUrl);
+ }
+
+ // 加载并应用壁纸
+ loadAndApplyWallpaper(imageUrl, downloadUrl = imageUrl) {
+ this.currentWallpaperUrl = downloadUrl;
+
+ const img = new Image();
+ img.crossOrigin = 'anonymous';
+
+ img.onload = () => {
+ try {
+ const avgColor = this.getImageAverageColor(img);
+ if (avgColor) {
+ this.applyThemeColor(avgColor);
+ } else {
+ Logger.logError('无法获取平均色,保持当前主题色');
+ }
+ } catch (e) {
+ Logger.logError(`更新主题色失败: ${e.message}`);
+ }
+
+ this.applyWallpaperTransition(imageUrl);
+ };
+
+ img.onerror = () => {
+ Logger.logError('壁纸加载失败,保持当前背景和主题');
+ this.isChangingBg = false;
+ };
+
+ img.src = imageUrl;
+ }
// 获取图片平均颜色
getImageAverageColor(img) {
@@ -98,8 +136,8 @@ class WallpaperManager {
this.isChangingBg = true;
- try {
- Logger.log('正在获取壁纸...');
+ try {
+ Logger.log('正在获取壁纸...');
const enabledSources = [];
if (this.wallPaperSources.international.enabled) enabledSources.push('international');
@@ -115,29 +153,17 @@ class WallpaperManager {
const source = this.wallPaperSources[randomSource];
const isChinese = randomSource === 'chinese';
- let githubUrl = '';
- const now = new Date();
- const currentYear = now.getFullYear();
- const currentMonth = now.getMonth() + 1;
-
- if (isChinese) {
- let randomYear, randomMonth;
- if (currentYear === source.startYear) {
- randomMonth = Math.floor(Math.random() * (currentMonth - source.startMonth + 1)) + source.startMonth;
- randomYear = currentYear;
- } else {
- const totalMonths = (currentYear - source.startYear) * 12 + currentMonth - source.startMonth;
- const randomOffset = Math.floor(Math.random() * (totalMonths + 1));
- randomYear = source.startYear + Math.floor(randomOffset / 12);
- randomMonth = source.startMonth + (randomOffset % 12);
-
- if (randomYear === currentYear && randomMonth > currentMonth) {
- randomMonth = currentMonth;
- }
- }
-
- githubUrl = `https://raw.githubusercontent.com/niumoo/bing-wallpaper/refs/heads/main/zh-cn/picture/${randomYear}-${String(randomMonth).padStart(2, '0')}/README.md`;
- } else {
+ let githubUrl = '';
+ const now = new Date();
+ const currentYear = now.getFullYear();
+ const currentMonth = now.getMonth() + 1;
+
+ if (isChinese) {
+ const randomHistoryUrl = `https://bing.img.run/rand_uhd.php?t=${Date.now()}`;
+ this.currentWallpaperApiUrl = randomHistoryUrl;
+ this.loadAndApplyWallpaper(randomHistoryUrl, 'https://bing.img.run/rand_uhd.php');
+ return;
+ } else {
const randomYear = Math.floor(Math.random() * (currentYear - source.startYear + 1)) + source.startYear;
let randomMonth;
if (randomYear === source.startYear) {
@@ -161,36 +187,12 @@ class WallpaperManager {
const markdownContent = await response.text();
const wallpapers = this.parseMarkdownForWallpapers(markdownContent);
- if (wallpapers.length > 0) {
- const randomIndex = Math.floor(Math.random() * wallpapers.length);
- const selectedWallpaper = wallpapers[randomIndex];
- this.currentWallpaperUrl = selectedWallpaper.url;
-
- const img = new Image();
- img.crossOrigin = "anonymous";
-
- img.onload = () => {
- try {
- const avgColor = this.getImageAverageColor(img);
- if (avgColor) {
- this.applyThemeColor(avgColor);
- } else {
- Logger.logError('无法获取平均色,保持当前主题色');
- }
- } catch (e) {
- Logger.logError(`更新主题色失败: ${e.message}`);
- }
-
- this.applyWallpaperTransition(selectedWallpaper.url);
- };
-
- img.onerror = () => {
- Logger.logError('壁纸加载失败,保持当前背景和主题');
- this.isChangingBg = false;
- };
-
- img.src = selectedWallpaper.url;
- } else {
+ if (wallpapers.length > 0) {
+ const randomIndex = Math.floor(Math.random() * wallpapers.length);
+ const selectedWallpaper = wallpapers[randomIndex];
+ this.currentWallpaperApiUrl = selectedWallpaper.url;
+ this.loadAndApplyWallpaper(selectedWallpaper.url);
+ } else {
Logger.logError('未找到壁纸数据,保持当前背景和主题');
this.isChangingBg = false;
}
From 3e5364c75f37a665e84441230a23514f6af8b960 Mon Sep 17 00:00:00 2001
From: MaJiangla <2652352927@qq.com>
Date: Fri, 13 Feb 2026 23:00:40 +0800
Subject: [PATCH 2/2] =?UTF-8?q?=E4=BF=AE=E5=A4=8D=E4=B8=AD=E5=9B=BD?=
=?UTF-8?q?=E7=89=88=E5=A3=81=E7=BA=B8=E6=8E=A5=E5=8F=A3=E7=9A=84=20CORS?=
=?UTF-8?q?=20=E5=8A=A0=E8=BD=BD=E9=97=AE=E9=A2=98?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
wallpaper.js | 429 ++++++++++++++++++++++++++-------------------------
1 file changed, 217 insertions(+), 212 deletions(-)
diff --git a/wallpaper.js b/wallpaper.js
index 5aeb411..b2395b2 100644
--- a/wallpaper.js
+++ b/wallpaper.js
@@ -1,5 +1,5 @@
-// 壁纸管理模块
-class WallpaperManager {
+// 壁纸管理模块
+class WallpaperManager {
constructor() {
this.currentWallpaperUrl = '';
this.currentWallpaperApiUrl = '';
@@ -12,26 +12,31 @@ class WallpaperManager {
setChineseDailyBackground() {
const dailyWallpaperUrl = 'https://bing.img.run/uhd.php';
this.currentWallpaperApiUrl = dailyWallpaperUrl;
- this.loadAndApplyWallpaper(dailyWallpaperUrl, dailyWallpaperUrl);
+ this.loadAndApplyWallpaper(dailyWallpaperUrl, dailyWallpaperUrl, { useCors: false, extractTheme: false });
}
// 加载并应用壁纸
- loadAndApplyWallpaper(imageUrl, downloadUrl = imageUrl) {
+ loadAndApplyWallpaper(imageUrl, downloadUrl = imageUrl, options = {}) {
+ const { useCors = true, extractTheme = true } = options;
this.currentWallpaperUrl = downloadUrl;
const img = new Image();
- img.crossOrigin = 'anonymous';
+ if (useCors) {
+ img.crossOrigin = 'anonymous';
+ }
img.onload = () => {
- try {
- const avgColor = this.getImageAverageColor(img);
- if (avgColor) {
- this.applyThemeColor(avgColor);
- } else {
- Logger.logError('无法获取平均色,保持当前主题色');
+ if (extractTheme) {
+ try {
+ const avgColor = this.getImageAverageColor(img);
+ if (avgColor) {
+ this.applyThemeColor(avgColor);
+ } else {
+ Logger.logError('无法获取平均色,保持当前主题色');
+ }
+ } catch (e) {
+ Logger.logError(`更新主题色失败: ${e.message}`);
}
- } catch (e) {
- Logger.logError(`更新主题色失败: ${e.message}`);
}
this.applyWallpaperTransition(imageUrl);
@@ -44,115 +49,115 @@ class WallpaperManager {
img.src = imageUrl;
}
-
- // 获取图片平均颜色
- getImageAverageColor(img) {
- try {
- const canvas = document.createElement('canvas');
- const ctx = canvas.getContext('2d');
- canvas.width = 50;
- canvas.height = 50;
-
- ctx.drawImage(img, 0, 0, 50, 50);
-
- const imageData = ctx.getImageData(0, 0, 50, 50);
- const data = imageData.data;
-
- let r = 0, g = 0, b = 0;
- const pixelCount = 50 * 50;
-
- for (let i = 0; i < data.length; i += 4) {
- r += data[i];
- g += data[i + 1];
- b += data[i + 2];
- }
-
- r = Math.floor(r / pixelCount);
- g = Math.floor(g / pixelCount);
- b = Math.floor(b / pixelCount);
-
- Logger.log(`平均颜色: RGB(${r}, ${g}, ${b})`);
- return { r, g, b };
- } catch (error) {
- Logger.logError(`获取颜色失败: ${error.message}`);
- return null;
- }
- }
-
- // 应用主题颜色到所有元素
- applyThemeColor(color) {
- if (!color) {
- Logger.log('保持当前主题颜色不变');
- return;
- }
-
- const adjustedColor = Utils.ensureContrastWithWhite(color.r, color.g, color.b);
- this.currentThemeColor = adjustedColor;
-
- const primaryColor = `rgb(${adjustedColor.r}, ${adjustedColor.g}, ${adjustedColor.b})`;
- const secondaryColor = `rgba(${adjustedColor.r}, ${adjustedColor.g}, ${adjustedColor.b}, 0.8)`;
- const thirdColor = `rgba(${adjustedColor.r}, ${adjustedColor.g}, ${adjustedColor.b}, 0.4)`;
-
- document.documentElement.style.setProperty('--primary-color', primaryColor);
- document.documentElement.style.setProperty('--secondary-color', secondaryColor);
- document.documentElement.style.setProperty('--third-color', thirdColor);
-
- const whiteContrast = Utils.getContrastRatio(adjustedColor.r, adjustedColor.g, adjustedColor.b, 255, 255, 255);
- Logger.log(`主题色: RGB(${adjustedColor.r}, ${adjustedColor.g}, ${adjustedColor.b}), 对比度: ${whiteContrast.toFixed(2)}`);
- }
-
- // 更新壁纸源选择
- updateWallpaperSources(internationalChecked, chineseChecked) {
- this.wallPaperSources.international.enabled = internationalChecked;
- this.wallPaperSources.chinese.enabled = chineseChecked;
-
- if (!internationalChecked && !chineseChecked) {
- this.wallPaperSources.chinese.enabled = true;
- Logger.log('至少选择一个');
- return true; // 表示需要更新UI
- }
- return false;
- }
-
- // 解析壁纸数据
- parseMarkdownForWallpapers(markdown) {
- const wallpapers = [];
- const regex = /!\[.*?\]\((.*?)\)(\d{4}-\d{2}-\d{2}) \[download 4k\]\((.*?)\)/g;
- let match;
-
- while ((match = regex.exec(markdown)) !== null) {
- const fullUrl = match[3];
- if (fullUrl && fullUrl.startsWith('http')) {
- wallpapers.push({ url: fullUrl });
- }
- }
-
- return wallpapers;
- }
-
- // 获取随机壁纸
- async setRandomBingBackground() {
- if (this.isChangingBg) return;
-
- this.isChangingBg = true;
-
+
+ // 获取图片平均颜色
+ getImageAverageColor(img) {
+ try {
+ const canvas = document.createElement('canvas');
+ const ctx = canvas.getContext('2d');
+ canvas.width = 50;
+ canvas.height = 50;
+
+ ctx.drawImage(img, 0, 0, 50, 50);
+
+ const imageData = ctx.getImageData(0, 0, 50, 50);
+ const data = imageData.data;
+
+ let r = 0, g = 0, b = 0;
+ const pixelCount = 50 * 50;
+
+ for (let i = 0; i < data.length; i += 4) {
+ r += data[i];
+ g += data[i + 1];
+ b += data[i + 2];
+ }
+
+ r = Math.floor(r / pixelCount);
+ g = Math.floor(g / pixelCount);
+ b = Math.floor(b / pixelCount);
+
+ Logger.log(`平均颜色: RGB(${r}, ${g}, ${b})`);
+ return { r, g, b };
+ } catch (error) {
+ Logger.logError(`获取颜色失败: ${error.message}`);
+ return null;
+ }
+ }
+
+ // 应用主题颜色到所有元素
+ applyThemeColor(color) {
+ if (!color) {
+ Logger.log('保持当前主题颜色不变');
+ return;
+ }
+
+ const adjustedColor = Utils.ensureContrastWithWhite(color.r, color.g, color.b);
+ this.currentThemeColor = adjustedColor;
+
+ const primaryColor = `rgb(${adjustedColor.r}, ${adjustedColor.g}, ${adjustedColor.b})`;
+ const secondaryColor = `rgba(${adjustedColor.r}, ${adjustedColor.g}, ${adjustedColor.b}, 0.8)`;
+ const thirdColor = `rgba(${adjustedColor.r}, ${adjustedColor.g}, ${adjustedColor.b}, 0.4)`;
+
+ document.documentElement.style.setProperty('--primary-color', primaryColor);
+ document.documentElement.style.setProperty('--secondary-color', secondaryColor);
+ document.documentElement.style.setProperty('--third-color', thirdColor);
+
+ const whiteContrast = Utils.getContrastRatio(adjustedColor.r, adjustedColor.g, adjustedColor.b, 255, 255, 255);
+ Logger.log(`主题色: RGB(${adjustedColor.r}, ${adjustedColor.g}, ${adjustedColor.b}), 对比度: ${whiteContrast.toFixed(2)}`);
+ }
+
+ // 更新壁纸源选择
+ updateWallpaperSources(internationalChecked, chineseChecked) {
+ this.wallPaperSources.international.enabled = internationalChecked;
+ this.wallPaperSources.chinese.enabled = chineseChecked;
+
+ if (!internationalChecked && !chineseChecked) {
+ this.wallPaperSources.chinese.enabled = true;
+ Logger.log('至少选择一个');
+ return true; // 表示需要更新UI
+ }
+ return false;
+ }
+
+ // 解析壁纸数据
+ parseMarkdownForWallpapers(markdown) {
+ const wallpapers = [];
+ const regex = /!\[.*?\]\((.*?)\)(\d{4}-\d{2}-\d{2}) \[download 4k\]\((.*?)\)/g;
+ let match;
+
+ while ((match = regex.exec(markdown)) !== null) {
+ const fullUrl = match[3];
+ if (fullUrl && fullUrl.startsWith('http')) {
+ wallpapers.push({ url: fullUrl });
+ }
+ }
+
+ return wallpapers;
+ }
+
+ // 获取随机壁纸
+ async setRandomBingBackground() {
+ if (this.isChangingBg) return;
+
+ this.isChangingBg = true;
+
try {
Logger.log('正在获取壁纸...');
-
- const enabledSources = [];
- if (this.wallPaperSources.international.enabled) enabledSources.push('international');
- if (this.wallPaperSources.chinese.enabled) enabledSources.push('chinese');
-
- if (enabledSources.length === 0) {
- Logger.logError('未选择壁纸源');
- this.isChangingBg = false;
- return;
- }
-
- const randomSource = enabledSources[Math.floor(Math.random() * enabledSources.length)];
- const source = this.wallPaperSources[randomSource];
- const isChinese = randomSource === 'chinese';
-
+
+ const enabledSources = [];
+ if (this.wallPaperSources.international.enabled) enabledSources.push('international');
+ if (this.wallPaperSources.chinese.enabled) enabledSources.push('chinese');
+
+ if (enabledSources.length === 0) {
+ Logger.logError('未选择壁纸源');
+ this.isChangingBg = false;
+ return;
+ }
+
+ const randomSource = enabledSources[Math.floor(Math.random() * enabledSources.length)];
+ const source = this.wallPaperSources[randomSource];
+ const isChinese = randomSource === 'chinese';
+
let githubUrl = '';
const now = new Date();
const currentYear = now.getFullYear();
@@ -161,103 +166,103 @@ class WallpaperManager {
if (isChinese) {
const randomHistoryUrl = `https://bing.img.run/rand_uhd.php?t=${Date.now()}`;
this.currentWallpaperApiUrl = randomHistoryUrl;
- this.loadAndApplyWallpaper(randomHistoryUrl, 'https://bing.img.run/rand_uhd.php');
+ this.loadAndApplyWallpaper(randomHistoryUrl, 'https://bing.img.run/rand_uhd.php', { useCors: false, extractTheme: false });
return;
} else {
- const randomYear = Math.floor(Math.random() * (currentYear - source.startYear + 1)) + source.startYear;
- let randomMonth;
- if (randomYear === source.startYear) {
- randomMonth = Math.floor(Math.random() * (12 - source.startMonth + 1)) + source.startMonth;
- } else if (randomYear === currentYear) {
- randomMonth = Math.floor(Math.random() * currentMonth) + 1;
- } else {
- randomMonth = Math.floor(Math.random() * 12) + 1;
- }
-
- githubUrl = `https://raw.githubusercontent.com/niumoo/bing-wallpaper/refs/heads/main/picture/${randomYear}-${String(randomMonth).padStart(2, '0')}/README.md`;
- }
-
- Logger.log(`请求壁纸数据: ${githubUrl}`);
- const response = await fetch(githubUrl, { cache: 'no-cache' });
-
- if (!response.ok) {
- throw new Error(`HTTP ${response.status}: ${response.statusText}`);
- }
-
- const markdownContent = await response.text();
- const wallpapers = this.parseMarkdownForWallpapers(markdownContent);
-
+ const randomYear = Math.floor(Math.random() * (currentYear - source.startYear + 1)) + source.startYear;
+ let randomMonth;
+ if (randomYear === source.startYear) {
+ randomMonth = Math.floor(Math.random() * (12 - source.startMonth + 1)) + source.startMonth;
+ } else if (randomYear === currentYear) {
+ randomMonth = Math.floor(Math.random() * currentMonth) + 1;
+ } else {
+ randomMonth = Math.floor(Math.random() * 12) + 1;
+ }
+
+ githubUrl = `https://raw.githubusercontent.com/niumoo/bing-wallpaper/refs/heads/main/picture/${randomYear}-${String(randomMonth).padStart(2, '0')}/README.md`;
+ }
+
+ Logger.log(`请求壁纸数据: ${githubUrl}`);
+ const response = await fetch(githubUrl, { cache: 'no-cache' });
+
+ if (!response.ok) {
+ throw new Error(`HTTP ${response.status}: ${response.statusText}`);
+ }
+
+ const markdownContent = await response.text();
+ const wallpapers = this.parseMarkdownForWallpapers(markdownContent);
+
if (wallpapers.length > 0) {
const randomIndex = Math.floor(Math.random() * wallpapers.length);
const selectedWallpaper = wallpapers[randomIndex];
this.currentWallpaperApiUrl = selectedWallpaper.url;
this.loadAndApplyWallpaper(selectedWallpaper.url);
} else {
- Logger.logError('未找到壁纸数据,保持当前背景和主题');
- this.isChangingBg = false;
- }
-
- } catch (error) {
- Logger.logError(`设置随机壁纸失败: ${error.message}`);
- this.isChangingBg = false;
- }
- }
-
- // 应用壁纸过渡
- applyWallpaperTransition(url) {
- const currentBg = document.getElementById('current-bg');
- const newBg = document.getElementById('new-bg');
-
- newBg.style.backgroundImage = `url('${url}')`;
- newBg.classList.remove('fade-in');
- void newBg.offsetWidth;
- newBg.classList.add('fade-in');
- newBg.style.opacity = '1';
-
- setTimeout(() => {
- currentBg.style.backgroundImage = newBg.style.backgroundImage;
-
- setTimeout(() => {
- newBg.style.opacity = '0';
- newBg.style.backgroundImage = '';
- Logger.logWallpaper(this.currentWallpaperUrl);
- this.isChangingBg = false;
- }, 100);
- }, 200);
- }
-
- // 下载当前壁纸
- async downloadCurrentWallpaper() {
- if (!this.currentWallpaperUrl) {
- Logger.logError('无当前壁纸可下载');
- return;
- }
-
- try {
- Logger.log('开始下载当前壁纸...');
- const response = await fetch(this.currentWallpaperUrl);
- if (!response.ok) {
- throw new Error(`HTTP ${response.status}: ${response.statusText}`);
- }
-
- const blob = await response.blob();
- const url = window.URL.createObjectURL(blob);
- const a = document.createElement('a');
- a.href = url;
- a.download = `bing-wallpaper-${new Date().toISOString().slice(0,10)}.jpg`;
-
- document.body.appendChild(a);
- a.click();
-
- setTimeout(() => {
- window.URL.revokeObjectURL(url);
- document.body.removeChild(a);
- }, 100);
-
- Logger.logSuccess('壁纸下载完成');
- } catch (error) {
- Logger.logError(`壁纸下载失败: ${error.message}`);
- }
- }
-
-}
+ Logger.logError('未找到壁纸数据,保持当前背景和主题');
+ this.isChangingBg = false;
+ }
+
+ } catch (error) {
+ Logger.logError(`设置随机壁纸失败: ${error.message}`);
+ this.isChangingBg = false;
+ }
+ }
+
+ // 应用壁纸过渡
+ applyWallpaperTransition(url) {
+ const currentBg = document.getElementById('current-bg');
+ const newBg = document.getElementById('new-bg');
+
+ newBg.style.backgroundImage = `url('${url}')`;
+ newBg.classList.remove('fade-in');
+ void newBg.offsetWidth;
+ newBg.classList.add('fade-in');
+ newBg.style.opacity = '1';
+
+ setTimeout(() => {
+ currentBg.style.backgroundImage = newBg.style.backgroundImage;
+
+ setTimeout(() => {
+ newBg.style.opacity = '0';
+ newBg.style.backgroundImage = '';
+ Logger.logWallpaper(this.currentWallpaperUrl);
+ this.isChangingBg = false;
+ }, 100);
+ }, 200);
+ }
+
+ // 下载当前壁纸
+ async downloadCurrentWallpaper() {
+ if (!this.currentWallpaperUrl) {
+ Logger.logError('无当前壁纸可下载');
+ return;
+ }
+
+ try {
+ Logger.log('开始下载当前壁纸...');
+ const response = await fetch(this.currentWallpaperUrl);
+ if (!response.ok) {
+ throw new Error(`HTTP ${response.status}: ${response.statusText}`);
+ }
+
+ const blob = await response.blob();
+ const url = window.URL.createObjectURL(blob);
+ const a = document.createElement('a');
+ a.href = url;
+ a.download = `bing-wallpaper-${new Date().toISOString().slice(0,10)}.jpg`;
+
+ document.body.appendChild(a);
+ a.click();
+
+ setTimeout(() => {
+ window.URL.revokeObjectURL(url);
+ document.body.removeChild(a);
+ }, 100);
+
+ Logger.logSuccess('壁纸下载完成');
+ } catch (error) {
+ Logger.logError(`壁纸下载失败: ${error.message}`);
+ }
+ }
+
+}