twskin 0.5.5 → 0.5.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +11 -0
- package/package.json +1 -1
- package/runtime/injector.mjs +1 -1
- package/runtime/manifest.json +6 -6
- package/runtime/skin.js +128 -27
- package/runtime/styles/manager.css +47 -22
package/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,17 @@ All notable changes to this package are documented here. This project follows
|
|
|
5
5
|
|
|
6
6
|
## [Unreleased]
|
|
7
7
|
|
|
8
|
+
## [0.5.6] - 2026-07-27
|
|
9
|
+
|
|
10
|
+
### Changed
|
|
11
|
+
|
|
12
|
+
- Reorganized Theme Manager controls by ownership: current-theme settings now
|
|
13
|
+
contain only per-theme appearance controls, while catalog updates, local theme
|
|
14
|
+
scanning, and restoring TRAE's native appearance live in Theme Library Settings.
|
|
15
|
+
- Moved Theme Library Settings to a compact, accessible gear button in the
|
|
16
|
+
manager header. Manual update checks and their status now live there, keeping
|
|
17
|
+
the theme gallery focused on browsing and switching themes.
|
|
18
|
+
|
|
8
19
|
## [0.5.5] - 2026-07-27
|
|
9
20
|
|
|
10
21
|
### Added
|
package/package.json
CHANGED
package/runtime/injector.mjs
CHANGED
|
@@ -16,7 +16,7 @@ import { spawnSync } from "node:child_process";
|
|
|
16
16
|
import { fileURLToPath } from "node:url";
|
|
17
17
|
|
|
18
18
|
const ROOT = path.dirname(fileURLToPath(import.meta.url));
|
|
19
|
-
const VERSION = "0.5.
|
|
19
|
+
const VERSION = "0.5.6";
|
|
20
20
|
const DATA_DIR = process.env.TWSKIN_DATA_DIR || path.join(os.homedir(), ".trae-work-skin");
|
|
21
21
|
|
|
22
22
|
function parseArgs(argv) {
|
package/runtime/manifest.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"schemaVersion": 1,
|
|
3
|
-
"packageVersion": "0.5.
|
|
3
|
+
"packageVersion": "0.5.6",
|
|
4
4
|
"themesBundled": false,
|
|
5
5
|
"files": [
|
|
6
6
|
{
|
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
{
|
|
12
12
|
"path": "injector.mjs",
|
|
13
13
|
"size": 31308,
|
|
14
|
-
"sha256": "
|
|
14
|
+
"sha256": "4256fcebb123657be1ba2968dae6d3904f54618d120e7d9f62b02796fcdebed0"
|
|
15
15
|
},
|
|
16
16
|
{
|
|
17
17
|
"path": "restore.sh",
|
|
@@ -20,8 +20,8 @@
|
|
|
20
20
|
},
|
|
21
21
|
{
|
|
22
22
|
"path": "skin.js",
|
|
23
|
-
"size":
|
|
24
|
-
"sha256": "
|
|
23
|
+
"size": 61967,
|
|
24
|
+
"sha256": "c4b177a30b7d0681c28324d8042e0e75972df71924120342a1b852a8e0ff5cf0"
|
|
25
25
|
},
|
|
26
26
|
{
|
|
27
27
|
"path": "start.sh",
|
|
@@ -35,8 +35,8 @@
|
|
|
35
35
|
},
|
|
36
36
|
{
|
|
37
37
|
"path": "styles/manager.css",
|
|
38
|
-
"size":
|
|
39
|
-
"sha256": "
|
|
38
|
+
"size": 19040,
|
|
39
|
+
"sha256": "4a8acef7f2dddbcd61e5b1460a7639bd52478e9131099eb699874e9bffb0c87c"
|
|
40
40
|
},
|
|
41
41
|
{
|
|
42
42
|
"path": "token-map.mjs",
|
package/runtime/skin.js
CHANGED
|
@@ -665,24 +665,31 @@ ${selector} {
|
|
|
665
665
|
const configToggle = document.createElement("button");
|
|
666
666
|
configToggle.className = "ds-config-toggle";
|
|
667
667
|
configToggle.type = "button";
|
|
668
|
-
configToggle.textContent = "
|
|
668
|
+
configToggle.textContent = "当前主题";
|
|
669
669
|
configToggle.title = "查看当前主题配置";
|
|
670
|
+
const globalToggle = document.createElement("button");
|
|
671
|
+
globalToggle.className = "ds-global-toggle";
|
|
672
|
+
globalToggle.type = "button";
|
|
673
|
+
globalToggle.setAttribute("aria-label", "主题库设置");
|
|
674
|
+
globalToggle.setAttribute("aria-pressed", "false");
|
|
675
|
+
globalToggle.title = "主题库设置";
|
|
676
|
+
globalToggle.innerHTML = '<svg viewBox="0 0 24 24" aria-hidden="true"><path d="M12 15.5a3.5 3.5 0 1 0 0-7 3.5 3.5 0 0 0 0 7Z"/><path d="m19.4 15 .1 1.7-2.1 2.1-1.7-.1-1.2 1-.4 1.6h-3l-.4-1.6-1.2-1-1.7.1-2.1-2.1.1-1.7-1-1.2L3 13.4v-3l1.6-.4 1-1.2-.1-1.7 2.1-2.1 1.7.1 1.2-1 .4-1.6h3l.4 1.6 1.2 1 1.7-.1 2.1 2.1-.1 1.7 1 1.2 1.6.4v3l-1.6.4-1 1.2Z"/></svg>';
|
|
670
677
|
const syncButton = document.createElement("button");
|
|
671
678
|
syncButton.className = "ds-sync";
|
|
672
679
|
syncButton.type = "button";
|
|
673
|
-
syncButton.textContent = "
|
|
680
|
+
syncButton.textContent = "检查更新";
|
|
674
681
|
syncButton.title = "检查官方主题更新";
|
|
675
682
|
const reloadButton = document.createElement("button");
|
|
676
|
-
reloadButton.className = "ds-reload";
|
|
683
|
+
reloadButton.className = "ds-local-reload";
|
|
677
684
|
reloadButton.type = "button";
|
|
678
|
-
reloadButton.
|
|
685
|
+
reloadButton.textContent = "重新扫描本地主题";
|
|
679
686
|
reloadButton.title = "重新加载主题目录(新主题热加载)";
|
|
680
687
|
const closeButton = document.createElement("button");
|
|
681
688
|
closeButton.className = "ds-close";
|
|
682
689
|
closeButton.type = "button";
|
|
683
690
|
closeButton.textContent = "×";
|
|
684
691
|
closeButton.title = "关闭 (Esc)";
|
|
685
|
-
headerActions.append(
|
|
692
|
+
headerActions.append(configToggle, globalToggle, closeButton);
|
|
686
693
|
header.append(headerText, headerActions);
|
|
687
694
|
const panelBody = document.createElement("div");
|
|
688
695
|
panelBody.className = "ds-body";
|
|
@@ -717,6 +724,29 @@ ${selector} {
|
|
|
717
724
|
blurSwitch.setAttribute("role", "switch");
|
|
718
725
|
blurSwitch.setAttribute("aria-label", "面板模糊");
|
|
719
726
|
blurRow.append(blurCopy, blurSwitch);
|
|
727
|
+
const globalView = document.createElement("div");
|
|
728
|
+
globalView.className = "ds-global-view";
|
|
729
|
+
const globalHead = document.createElement("div");
|
|
730
|
+
globalHead.className = "ds-global-head";
|
|
731
|
+
const globalTitle = document.createElement("div");
|
|
732
|
+
globalTitle.className = "ds-global-title";
|
|
733
|
+
globalTitle.textContent = "主题库设置";
|
|
734
|
+
const globalDesc = document.createElement("div");
|
|
735
|
+
globalDesc.className = "ds-global-desc";
|
|
736
|
+
globalDesc.textContent = "管理所有主题共用的更新与本地目录";
|
|
737
|
+
globalHead.append(globalTitle, globalDesc);
|
|
738
|
+
const checkRow = document.createElement("div");
|
|
739
|
+
checkRow.className = "ds-setting-row";
|
|
740
|
+
const checkCopy = document.createElement("div");
|
|
741
|
+
checkCopy.className = "ds-setting-copy";
|
|
742
|
+
const checkLabel = document.createElement("div");
|
|
743
|
+
checkLabel.className = "ds-setting-label";
|
|
744
|
+
checkLabel.textContent = "检查官方主题更新";
|
|
745
|
+
const checkDesc = document.createElement("div");
|
|
746
|
+
checkDesc.className = "ds-setting-desc";
|
|
747
|
+
checkDesc.setAttribute("aria-live", "polite");
|
|
748
|
+
checkCopy.append(checkLabel, checkDesc);
|
|
749
|
+
checkRow.append(checkCopy, syncButton);
|
|
720
750
|
const updateRow = document.createElement("div");
|
|
721
751
|
updateRow.className = "ds-setting-row";
|
|
722
752
|
const updateCopy = document.createElement("div");
|
|
@@ -734,6 +764,18 @@ ${selector} {
|
|
|
734
764
|
updateSwitch.setAttribute("role", "switch");
|
|
735
765
|
updateSwitch.setAttribute("aria-label", "自动更新官方主题");
|
|
736
766
|
updateRow.append(updateCopy, updateSwitch);
|
|
767
|
+
const localThemesRow = document.createElement("div");
|
|
768
|
+
localThemesRow.className = "ds-setting-row ds-local-themes-row";
|
|
769
|
+
const localThemesCopy = document.createElement("div");
|
|
770
|
+
localThemesCopy.className = "ds-setting-copy";
|
|
771
|
+
const localThemesLabel = document.createElement("div");
|
|
772
|
+
localThemesLabel.className = "ds-setting-label";
|
|
773
|
+
localThemesLabel.textContent = "本地主题";
|
|
774
|
+
const localThemesDesc = document.createElement("div");
|
|
775
|
+
localThemesDesc.className = "ds-setting-desc";
|
|
776
|
+
localThemesDesc.textContent = "新增或修改 themes/ 目录后重新读取";
|
|
777
|
+
localThemesCopy.append(localThemesLabel, localThemesDesc);
|
|
778
|
+
localThemesRow.append(localThemesCopy, reloadButton);
|
|
737
779
|
const brightnessRow = document.createElement("div");
|
|
738
780
|
brightnessRow.className = "ds-setting-row ds-setting-row-slider";
|
|
739
781
|
const brightnessHead = document.createElement("div");
|
|
@@ -794,8 +836,21 @@ ${selector} {
|
|
|
794
836
|
resetActions.className = "ds-reset-actions";
|
|
795
837
|
resetActions.append(resetCancel, resetConfig);
|
|
796
838
|
configHead.append(configName, copyConfig);
|
|
797
|
-
|
|
798
|
-
|
|
839
|
+
const restoreRow = document.createElement("div");
|
|
840
|
+
restoreRow.className = "ds-setting-row ds-restore-row";
|
|
841
|
+
const restoreCopy = document.createElement("div");
|
|
842
|
+
restoreCopy.className = "ds-setting-copy";
|
|
843
|
+
const restoreLabel = document.createElement("div");
|
|
844
|
+
restoreLabel.className = "ds-setting-label";
|
|
845
|
+
restoreLabel.textContent = "恢复原生外观";
|
|
846
|
+
const restoreDesc = document.createElement("div");
|
|
847
|
+
restoreDesc.className = "ds-setting-desc";
|
|
848
|
+
restoreDesc.textContent = "停止应用主题化,并恢复 TRAE 默认界面";
|
|
849
|
+
restoreCopy.append(restoreLabel, restoreDesc);
|
|
850
|
+
restoreRow.append(restoreCopy, resetActions);
|
|
851
|
+
configView.append(configHead, brightnessRow, mainOverlayRow, blurRow, configCode);
|
|
852
|
+
globalView.append(globalHead, syncBanner, checkRow, updateRow, localThemesRow, restoreRow);
|
|
853
|
+
panelBody.append(galleryView, configView, globalView);
|
|
799
854
|
|
|
800
855
|
// 分类 Tab(固定在头部下,不随列表滚动;选择持久化)
|
|
801
856
|
const CATEGORY_LS = `${LS_PREFIX}category`;
|
|
@@ -836,19 +891,25 @@ ${selector} {
|
|
|
836
891
|
const footerText = document.createElement("span");
|
|
837
892
|
footerText.className = "ds-footer-text";
|
|
838
893
|
footerText.textContent = `TRAE Work Skin v${VERSION}`;
|
|
839
|
-
footer.append(footerText
|
|
894
|
+
footer.append(footerText);
|
|
840
895
|
panel.append(header, tabsBar, panelBody, footer);
|
|
841
896
|
|
|
842
|
-
let
|
|
843
|
-
const
|
|
844
|
-
|
|
845
|
-
//
|
|
846
|
-
tabsBar.style.display =
|
|
847
|
-
galleryView.style.display =
|
|
848
|
-
configView.style.display =
|
|
849
|
-
|
|
850
|
-
configToggle.
|
|
897
|
+
let activeView = "gallery";
|
|
898
|
+
const showView = (view) => {
|
|
899
|
+
activeView = view;
|
|
900
|
+
// 详情页只呈现对应所有权范围的设置,画廊则恢复主题库操作与分类列表。
|
|
901
|
+
tabsBar.style.display = view === "gallery" ? "" : "none";
|
|
902
|
+
galleryView.style.display = view === "gallery" ? "" : "none";
|
|
903
|
+
configView.style.display = view === "theme" ? "block" : "none";
|
|
904
|
+
globalView.style.display = view === "global" ? "block" : "none";
|
|
905
|
+
configToggle.textContent = view === "gallery" ? "当前主题" : "主题";
|
|
906
|
+
configToggle.title = view === "gallery" ? "查看当前主题配置" : "返回主题列表";
|
|
907
|
+
globalToggle.classList.toggle("ds-global-toggle-active", view === "global");
|
|
908
|
+
globalToggle.setAttribute("aria-pressed", String(view === "global"));
|
|
909
|
+
globalToggle.title = view === "global" ? "返回主题列表" : "主题库设置";
|
|
910
|
+
renderThemeSyncState();
|
|
851
911
|
};
|
|
912
|
+
const showConfig = (open) => showView(open ? "theme" : "gallery");
|
|
852
913
|
renderCurrentConfig = (theme = findTheme(
|
|
853
914
|
(() => { try { return localStorage.getItem(LS_KEY); } catch { return null; } })(),
|
|
854
915
|
)) => {
|
|
@@ -883,12 +944,21 @@ ${selector} {
|
|
|
883
944
|
if (themeSyncState.phase === "error") return themeSyncState.message || "主题更新失败";
|
|
884
945
|
return "";
|
|
885
946
|
};
|
|
947
|
+
const SUCCESS_FEEDBACK_DURATION_MS = 4000;
|
|
948
|
+
let successFeedbackTimer = null;
|
|
949
|
+
const hasRecentSyncSuccess = () => {
|
|
950
|
+
if (themeSyncState.phase !== "success") return false;
|
|
951
|
+
const completedAt = Date.parse(themeSyncState.lastSuccessfulSyncAt || "");
|
|
952
|
+
return Number.isFinite(completedAt) && Date.now() - completedAt < SUCCESS_FEEDBACK_DURATION_MS;
|
|
953
|
+
};
|
|
886
954
|
const renderThemeSyncState = () => {
|
|
887
955
|
const phase = themeSyncState.phase || "idle";
|
|
888
956
|
const summary = syncSummary();
|
|
957
|
+
const updateCount = Number(themeSyncState.updateCount || 0);
|
|
958
|
+
const showSuccessFeedback = hasRecentSyncSuccess();
|
|
889
959
|
syncBanner.replaceChildren();
|
|
890
960
|
syncBanner.className = `ds-sync-banner ds-sync-${phase}`;
|
|
891
|
-
if (!summary || phase === "fresh" || phase === "idle") {
|
|
961
|
+
if (!summary || phase === "fresh" || phase === "idle" || (phase === "success" && !showSuccessFeedback) || activeView !== "global") {
|
|
892
962
|
syncBanner.style.display = "none";
|
|
893
963
|
} else {
|
|
894
964
|
syncBanner.style.display = "flex";
|
|
@@ -918,13 +988,31 @@ ${selector} {
|
|
|
918
988
|
syncBanner.append(retry);
|
|
919
989
|
}
|
|
920
990
|
}
|
|
921
|
-
syncButton.classList.toggle("ds-sync-pending",
|
|
991
|
+
syncButton.classList.toggle("ds-sync-pending", updateCount > 0);
|
|
922
992
|
syncButton.disabled = phase === "checking" || phase === "downloading" || phase === "installing";
|
|
923
993
|
syncButton.title = summary || "检查官方主题更新";
|
|
994
|
+
globalToggle.classList.toggle("ds-global-pending", updateCount > 0);
|
|
995
|
+
let checkStatusCopy = "尚未检查";
|
|
996
|
+
if (phase === "checking") checkStatusCopy = "正在检查更新…";
|
|
997
|
+
else if (phase === "update-available") checkStatusCopy = `发现 ${updateCount} 项更新`;
|
|
998
|
+
else if (phase === "success" && showSuccessFeedback) checkStatusCopy = "已完成同步";
|
|
999
|
+
else if (phase === "error") checkStatusCopy = "检查失败,可重试";
|
|
1000
|
+
else if (themeSyncState.lastCheckedAt) checkStatusCopy = `上次检查:${new Date(themeSyncState.lastCheckedAt).toLocaleString()}`;
|
|
1001
|
+
checkDesc.textContent = checkStatusCopy;
|
|
1002
|
+
if (successFeedbackTimer) {
|
|
1003
|
+
clearTimeout(successFeedbackTimer);
|
|
1004
|
+
successFeedbackTimer = null;
|
|
1005
|
+
}
|
|
1006
|
+
if (showSuccessFeedback) {
|
|
1007
|
+
const remaining = SUCCESS_FEEDBACK_DURATION_MS - (Date.now() - Date.parse(themeSyncState.lastSuccessfulSyncAt));
|
|
1008
|
+
successFeedbackTimer = setTimeout(() => {
|
|
1009
|
+
successFeedbackTimer = null;
|
|
1010
|
+
renderThemeSyncState();
|
|
1011
|
+
}, Math.max(0, remaining));
|
|
1012
|
+
}
|
|
924
1013
|
updateSwitch.setAttribute("aria-checked", String(Boolean(themeSyncState.autoUpdateThemes)));
|
|
925
1014
|
updateSwitch.title = themeSyncState.autoUpdateThemes ? "关闭官方主题自动更新" : "开启官方主题自动更新";
|
|
926
|
-
|
|
927
|
-
footerText.textContent = `TRAE Work Skin v${VERSION} · 主题更新:${checkedAt}`;
|
|
1015
|
+
footerText.textContent = `TRAE Work Skin v${VERSION}`;
|
|
928
1016
|
};
|
|
929
1017
|
renderBrightnessControl = (theme = findTheme(
|
|
930
1018
|
(() => { try { return localStorage.getItem(LS_KEY); } catch { return null; } })(),
|
|
@@ -952,8 +1040,16 @@ ${selector} {
|
|
|
952
1040
|
};
|
|
953
1041
|
configToggle.addEventListener("click", (event) => {
|
|
954
1042
|
event.stopPropagation();
|
|
955
|
-
|
|
956
|
-
|
|
1043
|
+
if (activeView === "gallery") {
|
|
1044
|
+
renderCurrentConfig();
|
|
1045
|
+
showView("theme");
|
|
1046
|
+
} else {
|
|
1047
|
+
showView("gallery");
|
|
1048
|
+
}
|
|
1049
|
+
});
|
|
1050
|
+
globalToggle.addEventListener("click", (event) => {
|
|
1051
|
+
event.stopPropagation();
|
|
1052
|
+
showView(activeView === "global" ? "gallery" : "global");
|
|
957
1053
|
});
|
|
958
1054
|
syncButton.addEventListener("click", (event) => {
|
|
959
1055
|
event.stopPropagation();
|
|
@@ -1070,7 +1166,7 @@ ${selector} {
|
|
|
1070
1166
|
card.dataset.category = theme.category || "其他";
|
|
1071
1167
|
const badge = document.createElement("span");
|
|
1072
1168
|
badge.className = "ds-badge";
|
|
1073
|
-
badge.textContent = "
|
|
1169
|
+
badge.textContent = "当前主题";
|
|
1074
1170
|
const preview = document.createElement("div");
|
|
1075
1171
|
preview.className = "ds-preview";
|
|
1076
1172
|
preview.style.backgroundImage = `url("${theme.art}")`;
|
|
@@ -1124,11 +1220,16 @@ ${selector} {
|
|
|
1124
1220
|
});
|
|
1125
1221
|
reloadButton.addEventListener("click", (e) => {
|
|
1126
1222
|
e.stopPropagation();
|
|
1127
|
-
if (reloadButton.classList.contains("ds-reload-loading")) return;
|
|
1128
|
-
reloadButton.classList.add("ds-reload-loading");
|
|
1223
|
+
if (reloadButton.classList.contains("ds-local-reload-loading")) return;
|
|
1224
|
+
reloadButton.classList.add("ds-local-reload-loading");
|
|
1225
|
+
const original = reloadButton.textContent;
|
|
1226
|
+
reloadButton.textContent = "正在扫描…";
|
|
1129
1227
|
// 守护进程轮询到这个标记后会重建主题目录、重新注入并重新打开面板
|
|
1130
1228
|
window.__TRAE_DREAM_SKIN_RELOAD_REQUEST__ = Date.now();
|
|
1131
|
-
setTimeout(() =>
|
|
1229
|
+
setTimeout(() => {
|
|
1230
|
+
reloadButton.classList.remove("ds-local-reload-loading");
|
|
1231
|
+
reloadButton.textContent = original;
|
|
1232
|
+
}, 6000);
|
|
1132
1233
|
});
|
|
1133
1234
|
window.__TRAE_DREAM_SKIN_SYNC_LISTENER__ && window.removeEventListener("trae-dream-skin-sync-state", window.__TRAE_DREAM_SKIN_SYNC_LISTENER__);
|
|
1134
1235
|
window.__TRAE_DREAM_SKIN_SYNC_LISTENER__ = () => {
|
|
@@ -59,37 +59,49 @@ body.trae-skin-v2 #trae-dream-skin-button {
|
|
|
59
59
|
}
|
|
60
60
|
#trae-dream-skin-panel .ds-header-actions { flex: 0 0 auto; display: flex; align-items: center; gap: 5px; }
|
|
61
61
|
#trae-dream-skin-panel .ds-config-toggle,
|
|
62
|
-
#trae-dream-skin-panel .ds-sync,
|
|
63
62
|
#trae-dream-skin-panel .ds-close,
|
|
64
|
-
#trae-dream-skin-panel .ds-reload
|
|
63
|
+
#trae-dream-skin-panel .ds-local-reload,
|
|
64
|
+
#trae-dream-skin-panel .ds-global-toggle {
|
|
65
65
|
border: 1px solid rgba(255, 255, 255, 0.18); border-radius: 6px;
|
|
66
66
|
color: inherit; background: rgba(255, 255, 255, 0.08);
|
|
67
67
|
font: inherit; cursor: pointer;
|
|
68
68
|
}
|
|
69
69
|
#trae-dream-skin-panel .ds-config-toggle { padding: 3px 7px; }
|
|
70
|
-
#trae-dream-skin-panel .ds-sync {
|
|
70
|
+
#trae-dream-skin-panel .ds-sync {
|
|
71
|
+
position: relative; flex: 0 0 auto; padding: 4px 8px; border-radius: 6px;
|
|
72
|
+
border: 1px solid rgba(124, 156, 255, 0.52); color: inherit;
|
|
73
|
+
background: rgba(124, 156, 255, 0.13); font: inherit; cursor: pointer;
|
|
74
|
+
}
|
|
71
75
|
#trae-dream-skin-panel .ds-sync.ds-sync-pending::after {
|
|
72
76
|
content: ""; position: absolute; top: -3px; right: -3px;
|
|
73
77
|
width: 6px; height: 6px; border-radius: 50%; background: #ff8d98;
|
|
74
78
|
border: 1px solid rgba(20, 22, 34, 0.9);
|
|
75
79
|
}
|
|
76
80
|
#trae-dream-skin-panel .ds-close,
|
|
77
|
-
#trae-dream-skin-panel .ds-reload
|
|
81
|
+
#trae-dream-skin-panel .ds-local-reload,
|
|
82
|
+
#trae-dream-skin-panel .ds-global-toggle {
|
|
78
83
|
box-sizing: border-box; width: 23px; height: 23px; padding: 0;
|
|
79
84
|
display: flex; align-items: center; justify-content: center;
|
|
80
85
|
font-size: 14px; line-height: 1;
|
|
81
86
|
}
|
|
87
|
+
#trae-dream-skin-panel .ds-local-reload {
|
|
88
|
+
width: auto; height: auto; padding: 4px 7px; font-size: 10px; line-height: 1.2;
|
|
89
|
+
}
|
|
90
|
+
#trae-dream-skin-panel .ds-global-toggle { position: relative; padding: 0; }
|
|
91
|
+
#trae-dream-skin-panel .ds-global-toggle svg { width: 14px; height: 14px; fill: none; stroke: currentColor; stroke-width: 1.75; stroke-linecap: round; stroke-linejoin: round; }
|
|
92
|
+
#trae-dream-skin-panel .ds-global-toggle.ds-global-toggle-active { background: rgba(124, 156, 255, 0.18); border-color: rgba(124, 156, 255, 0.56); }
|
|
93
|
+
#trae-dream-skin-panel .ds-global-toggle.ds-global-toggle-active:hover { background: rgba(124, 156, 255, 0.24); }
|
|
94
|
+
#trae-dream-skin-panel .ds-global-toggle.ds-global-pending::after {
|
|
95
|
+
content: ""; position: absolute; top: -3px; right: -3px; width: 6px; height: 6px;
|
|
96
|
+
border-radius: 50%; background: #ff8d98; border: 1px solid rgba(20, 22, 34, 0.9);
|
|
97
|
+
}
|
|
82
98
|
#trae-dream-skin-panel .ds-config-toggle:hover,
|
|
83
99
|
#trae-dream-skin-panel .ds-sync:hover:not(:disabled),
|
|
84
100
|
#trae-dream-skin-panel .ds-close:hover,
|
|
85
|
-
#trae-dream-skin-panel .ds-reload:hover
|
|
86
|
-
|
|
87
|
-
#trae-dream-skin-panel .ds-reload-icon { display: inline-block; line-height: 1; }
|
|
88
|
-
#trae-dream-skin-panel .ds-reload.ds-reload-loading { pointer-events: none; }
|
|
89
|
-
#trae-dream-skin-panel .ds-reload.ds-reload-loading .ds-reload-icon {
|
|
90
|
-
animation: trae-skin-spin 0.8s linear infinite;
|
|
91
|
-
}
|
|
101
|
+
#trae-dream-skin-panel .ds-local-reload:hover,
|
|
102
|
+
#trae-dream-skin-panel .ds-global-toggle:hover { background: rgba(255, 255, 255, 0.14); }
|
|
92
103
|
#trae-dream-skin-panel .ds-sync:disabled { opacity: 0.55; cursor: wait; }
|
|
104
|
+
#trae-dream-skin-panel .ds-local-reload.ds-local-reload-loading { opacity: 0.55; cursor: wait; }
|
|
93
105
|
#trae-dream-skin-panel .ds-body {
|
|
94
106
|
flex: 1 1 auto; overflow-y: auto; padding: 12px;
|
|
95
107
|
scrollbar-width: thin; scrollbar-color: rgba(255, 255, 255, 0.22) transparent;
|
|
@@ -118,7 +130,8 @@ body.trae-skin-v2 #trae-dream-skin-button {
|
|
|
118
130
|
}
|
|
119
131
|
#trae-dream-skin-panel .ds-sync-action:hover { background: rgba(255, 255, 255, 0.18); }
|
|
120
132
|
#trae-dream-skin-panel .ds-gallery-view,
|
|
121
|
-
#trae-dream-skin-panel .ds-config-view
|
|
133
|
+
#trae-dream-skin-panel .ds-config-view,
|
|
134
|
+
#trae-dream-skin-panel .ds-global-view { animation: trae-skin-fade-in 0.15s ease; }
|
|
122
135
|
/* 分类 Tab */
|
|
123
136
|
#trae-dream-skin-panel .ds-tabs {
|
|
124
137
|
flex: 0 0 auto; display: flex; gap: 4px;
|
|
@@ -156,7 +169,8 @@ body.trae-skin-v2 #trae-dream-skin-panel .ds-tab.ds-tab-active {
|
|
|
156
169
|
min-width: 0; opacity: 0.5;
|
|
157
170
|
overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
|
|
158
171
|
}
|
|
159
|
-
#trae-dream-skin-panel .ds-config-view
|
|
172
|
+
#trae-dream-skin-panel .ds-config-view,
|
|
173
|
+
#trae-dream-skin-panel .ds-global-view { display: none; }
|
|
160
174
|
#trae-dream-skin-panel .ds-config-head {
|
|
161
175
|
display: flex; align-items: center; justify-content: space-between;
|
|
162
176
|
gap: 8px; margin: 2px 2px 8px;
|
|
@@ -165,6 +179,9 @@ body.trae-skin-v2 #trae-dream-skin-panel .ds-tab.ds-tab-active {
|
|
|
165
179
|
min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
|
|
166
180
|
font-weight: 600;
|
|
167
181
|
}
|
|
182
|
+
#trae-dream-skin-panel .ds-global-head { margin: 2px 2px 8px; }
|
|
183
|
+
#trae-dream-skin-panel .ds-global-title { font-weight: 600; }
|
|
184
|
+
#trae-dream-skin-panel .ds-global-desc { margin-top: 1px; font-size: 10px; opacity: 0.58; }
|
|
168
185
|
#trae-dream-skin-panel .ds-setting-row {
|
|
169
186
|
display: flex; align-items: center; justify-content: space-between;
|
|
170
187
|
gap: 12px; margin: 0 2px 9px; padding: 8px 9px;
|
|
@@ -309,10 +326,12 @@ body.trae-skin-v2 #trae-dream-skin-panel .ds-tab.ds-tab-active {
|
|
|
309
326
|
#trae-dream-skin-panel .ds-badge {
|
|
310
327
|
flex: 0 0 auto;
|
|
311
328
|
display: none; align-items: center; gap: 3px;
|
|
312
|
-
padding:
|
|
313
|
-
background: #7c9cff; color: #0a0a0a;
|
|
329
|
+
padding: 0; color: #7c9cff;
|
|
314
330
|
font-size: 10px; font-weight: 600;
|
|
315
331
|
}
|
|
332
|
+
#trae-dream-skin-panel .ds-badge::before {
|
|
333
|
+
content: ""; width: 5px; height: 5px; border-radius: 50%; background: currentColor;
|
|
334
|
+
}
|
|
316
335
|
#trae-dream-skin-panel .ds-card.ds-active .ds-badge { display: flex; }
|
|
317
336
|
body.trae-skin-v2 #trae-dream-skin-panel {
|
|
318
337
|
color: var(--trae-skin-text-primary);
|
|
@@ -325,19 +344,16 @@ body.trae-skin-v2 #trae-dream-skin-panel .ds-card.ds-active {
|
|
|
325
344
|
border-color: var(--trae-skin-accent);
|
|
326
345
|
background: var(--trae-skin-accent-subtle);
|
|
327
346
|
}
|
|
328
|
-
body.trae-skin-v2 #trae-dream-skin-panel .ds-badge {
|
|
329
|
-
background: var(--trae-skin-accent);
|
|
330
|
-
color: var(--trae-skin-accent-on);
|
|
331
|
-
}
|
|
347
|
+
body.trae-skin-v2 #trae-dream-skin-panel .ds-badge { color: var(--trae-skin-accent); }
|
|
332
348
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-header { border-bottom-color: var(--trae-skin-border-subtle); }
|
|
333
349
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-footer { border-top-color: var(--trae-skin-border-subtle); }
|
|
334
350
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-body::-webkit-scrollbar-thumb { background: var(--trae-skin-scrollbar-thumb); }
|
|
335
351
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-body::-webkit-scrollbar-thumb:hover { background: var(--trae-skin-scrollbar-hover); }
|
|
336
352
|
body.trae-skin-effects-max #trae-dream-skin-panel .ds-header { padding-right: 16px; }
|
|
337
353
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-config-toggle,
|
|
338
|
-
body.trae-skin-v2 #trae-dream-skin-panel .ds-sync,
|
|
339
354
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-close,
|
|
340
|
-
body.trae-skin-v2 #trae-dream-skin-panel .ds-reload,
|
|
355
|
+
body.trae-skin-v2 #trae-dream-skin-panel .ds-local-reload,
|
|
356
|
+
body.trae-skin-v2 #trae-dream-skin-panel .ds-global-toggle,
|
|
341
357
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-copy-config,
|
|
342
358
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-reset-config,
|
|
343
359
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-reset-cancel {
|
|
@@ -348,13 +364,19 @@ body.trae-skin-v2 #trae-dream-skin-panel .ds-reset-cancel {
|
|
|
348
364
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-config-toggle:hover,
|
|
349
365
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-sync:hover:not(:disabled),
|
|
350
366
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-close:hover,
|
|
351
|
-
body.trae-skin-v2 #trae-dream-skin-panel .ds-reload:hover,
|
|
367
|
+
body.trae-skin-v2 #trae-dream-skin-panel .ds-local-reload:hover,
|
|
368
|
+
body.trae-skin-v2 #trae-dream-skin-panel .ds-global-toggle:hover,
|
|
352
369
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-copy-config:hover,
|
|
353
370
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-reset-config:hover,
|
|
354
371
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-reset-cancel:hover {
|
|
355
372
|
color: var(--trae-skin-accent);
|
|
356
373
|
border-color: var(--trae-skin-accent);
|
|
357
374
|
}
|
|
375
|
+
body.trae-skin-v2 #trae-dream-skin-panel .ds-global-toggle.ds-global-toggle-active {
|
|
376
|
+
color: var(--trae-skin-accent);
|
|
377
|
+
border-color: var(--trae-skin-accent);
|
|
378
|
+
background: var(--trae-skin-accent-subtle);
|
|
379
|
+
}
|
|
358
380
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-reset-config.ds-reset-armed {
|
|
359
381
|
color: var(--trae-skin-error);
|
|
360
382
|
border-color: var(--trae-skin-error);
|
|
@@ -371,6 +393,9 @@ body.trae-skin-v2 #trae-dream-skin-panel .ds-setting-row {
|
|
|
371
393
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-sync-banner {
|
|
372
394
|
border-color: var(--trae-skin-border-default); background: var(--trae-skin-info-subtle);
|
|
373
395
|
}
|
|
396
|
+
body.trae-skin-v2 #trae-dream-skin-panel .ds-sync {
|
|
397
|
+
border-color: var(--trae-skin-border-strong); background: var(--trae-skin-accent-subtle);
|
|
398
|
+
}
|
|
374
399
|
body.trae-skin-v2 #trae-dream-skin-panel .ds-sync-banner.ds-sync-error {
|
|
375
400
|
border-color: var(--trae-skin-error); background: color-mix(in srgb, var(--trae-skin-error) 12%, transparent);
|
|
376
401
|
}
|