dsh-background-by-model 0.9.1 → 0.10.0
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 +27 -1
- package/CHANGELOG.zh.md +27 -1
- package/README.md +41 -19
- package/README.zh.md +42 -20
- package/lib/client.js +634 -133
- package/lib/index.js +441 -62
- package/package.json +3 -2
package/CHANGELOG.md
CHANGED
|
@@ -1,6 +1,32 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
-
> The full release history lives here; the **Recent optimizations** section of [README.md](./README.md#recent-optimizations) lists only the two most recent releases (v0.
|
|
3
|
+
> The full release history lives here; the **Recent optimizations** section of [README.md](./README.md#recent-optimizations) lists only the two most recent releases (v0.10.0 / v0.9.2).
|
|
4
|
+
|
|
5
|
+
## v0.10.0
|
|
6
|
+
|
|
7
|
+
- **The config is written atomically, with a `.bak` of the last good file** — every save writes a temp file and renames it over the live one, rotating the current **parseable** file into `theme-config.json.bak` first. It used to be one in-place `writeFile`: a crash, a pulled cable or a full disk could leave half a JSON document, which `readConfig` answered with the factory defaults — and the next slider drag then persisted those defaults over the ruin. The original rules were gone for good.
|
|
8
|
+
- **A file that will not parse is restored from the backup, not treated as a fresh install** — when the live file is missing or corrupt and the `.bak` parses, that copy is read, written back to the live path, and reported once in the host log. Only when neither parses does the factory default answer.
|
|
9
|
+
- **The cleanup card still refuses on a corrupt config with no backup** — with a parseable backup it prunes against the backup's rules, because that is exactly the config the user is about to get back; with neither, the button stays disabled, because nothing on disk can be told apart from an orphan.
|
|
10
|
+
- **`resetStore` removes the `.bak` too** — leaving it behind would have the next read restore it, silently undoing the replacement the recommended profile exists to perform.
|
|
11
|
+
- **Opacity, brightness and blur moved from each RULE to each IMAGE** — the same layer the layout mode, the framing and the theme colour already live on: a daylight photo and a night shot in one rotation should not share one exposure. A schema-9 config's three rule-level values are lifted onto every one of its images on read, so upgrading changes nothing on screen.
|
|
12
|
+
- **`SCHEMA_VERSION` is 10** — the fields moved, and a schema-9 sanitizer rebuilds every image entry from the keys it knows: it would drop all three AND keep reading the rule-level values that no longer exist, so a dimmed wallpaper would come back at 100% in silence.
|
|
13
|
+
- **A blurred wallpaper no longer paints a dark rim around the viewport** — `blur()` treats everything outside the layer as transparent, so the edge came out half opaque and the page behind it showed through as a border that thickened with the slider. Each layer's box is now grown 2σ past the viewport (clipped by the container) with its placement moved back by the same amount, so the framing does not move.
|
|
14
|
+
- **A switch between two different opacity, brightness or blur values now animates** — each wallpaper layer keeps the filter of the picture it is painting, and the wallpaper's own opacity rides the switch instead of snapping to the incoming value on its first frame. Both used to be read live from the active image, so the outgoing picture was already wearing the incoming one's exposure before the fade ran: the transition was there, it just had nothing left to animate.
|
|
15
|
+
- **A repaint in the middle of a fade no longer cuts it short** — the steady opacity is mirrored in the render layer rather than read back from the store, so a theme re-registration or a panel re-render re-writes the value the fade is heading for.
|
|
16
|
+
- **Dragging a wallpaper's opacity, brightness or blur no longer repaints everything on every frame** — a drag frame writes only the property that field owns on the wallpaper layer, and the full `setRule` (skin, palette, wallpaper) runs once when the gesture ends. It used to be one full repaint per frame, which a large image made visibly slow.
|
|
17
|
+
- **`setWpOpacity` / `setWpFilter` have callers again** — the two zero-lag writers had none since the merged slider landed, while a comment and `check:image-mode` still asserted "two sites". `check:image-mode` now pins that the panel reaches them, and that a preview only touches the rule that is on screen.
|
|
18
|
+
- **The slider's preview and its commit are separate now** — `onInput` previews each frame and the commit rides the native `change` event, once. React's `onChange` for a range input is wired to that same `input` event, so committing from it was committing per frame.
|
|
19
|
+
- **Checks** — `check:node` gains a section on the atomic write and the backup (a corrupt file must not overwrite the good copy, no temp file survives, a reset takes the backup with it, a corrupt file heals from the copy) and pins the per-image lift, its clamps, the absent key and the holiday entry; `check:image-mode` pins that the render layer reads the image being PAINTED, that the panel writes the image being EDITED, that `defaultImage` is the only creation path, that the blurred edge is sampled off screen (the 2σ growth, written on the drag frame too), and that a layer carries its own picture's three effects rather than a live read.
|
|
20
|
+
|
|
21
|
+
## v0.9.2
|
|
22
|
+
|
|
23
|
+
- **The Config tab reports how many unreferenced images there are, and clears them** — images are stored at full fidelity, so an interrupted upload, a failed file deletion or a wholesale replacement can leave a `modelbg-<slot>` file that no rule references. That residue is invisible by construction: boot reads the slots the config names, so an orphaned file is never loaded, never painted and never reported anywhere.
|
|
24
|
+
- **Read first, delete second** — the card prints how much is cleanable and how many files that is, and only then offers the button; the figures describe what the press would free, not the store's total (a total file count reads as "delete all eight"). The sweep re-reads afterwards rather than subtracting, so a file that failed to delete still counts, and the toast names any that resisted.
|
|
25
|
+
- **The sweep asks nothing** — one press deletes. What goes is by definition referenced by no rule, and a "confirm?" here only teaches people to click through; the safety moved into the **gate** (an unreadable config disables the button). The numbers are still read first — announcing a size after deleting is the cleanup nobody would agree to.
|
|
26
|
+
- **A `modelbg-h-*` file is prunable** — that slot belongs to no config (the festival art lives in `holiday-cache/`, and the slot is read-only), so this is the only path that can ever remove one. `referencedSlots` deliberately takes RULES only, and `check:store` pins the call site so a future edit cannot add the holiday entries back.
|
|
27
|
+
- **An older host reads as "unknown", not "0 B"** — the node half answers two new methods (`storeUsage`, `pruneOrphans`), and a bundle talking to a node half from before them shows "restart DSH" instead of claiming a measurement nobody made.
|
|
28
|
+
- **`check:store`** — the two decisions (`referencedSlots` / `orphanSlots`) on plain node: a picture in use is never an orphan, `keep` only ever spares a slot (the gap between an upload's bytes and the rule entry that names them), and the client sends rule slots only. `check:node` covers the sweep through the real RPC handler.
|
|
29
|
+
- **The READMEs catch up with the checks** — they had been claiming ten since v0.8.1's `check:watchdogs` and `check:scheme` landed; both are now listed, as is `check:store`.
|
|
4
30
|
|
|
5
31
|
## v0.9.1
|
|
6
32
|
|
package/CHANGELOG.zh.md
CHANGED
|
@@ -1,6 +1,32 @@
|
|
|
1
1
|
# 更新日志
|
|
2
2
|
|
|
3
|
-
> 这里保留完整的历史记录;[README.zh.md](./README.zh.md#近期优化) 的「近期优化」一节只列最近两个版本(v0.
|
|
3
|
+
> 这里保留完整的历史记录;[README.zh.md](./README.zh.md#近期优化) 的「近期优化」一节只列最近两个版本(v0.10.0 / v0.9.2)。
|
|
4
|
+
|
|
5
|
+
## v0.10.0
|
|
6
|
+
|
|
7
|
+
- **配置改成原子写,并留一份 `.bak`** —— 每次保存先写临时文件、再改名覆盖,覆盖前把当前这份**能解析**的文件旋转成 `theme-config.json.bak`。此前是原地 `writeFile`:崩溃、断电或磁盘写满都可能留下半截 JSON,而 `readConfig` 遇到读不出来的文件会退回出厂默认,下一次拖动滑块就把这份默认写回去,原规则表彻底没了。
|
|
8
|
+
- **读不出来时从备份恢复,而不是当新装** —— 主文件缺失或损坏、而 `.bak` 能解析时,读它、把它写回主文件,并在宿主日志里说一句;两份都读不出时才是出厂默认。
|
|
9
|
+
- **清理卡在「没有备份的坏配置」上仍然拒绝删图** —— 有能解析的备份时,清理按备份里的规则走(那正是用户即将拿回的配置);一份都没有时按钮照旧是灰的,因为盘上没有任何东西能和孤儿区分开。
|
|
10
|
+
- **`resetStore` 连 `.bak` 一起删** —— 留着它,下一次读取会把它恢复回来,悄悄抵消掉「推荐配置」那次真正的替换。
|
|
11
|
+
- **透明度、亮度与模糊从「每条规则」下沉到「每张图」** —— 与布局模式、取景、主题色落在同一层:一组轮换里的一张白天照片和一张夜景,本来就不该共用一套曝光。schema-9 的规则级三个值在读取时一次性抬到它的每一张图上,所以升级不改变屏幕上任何东西。
|
|
12
|
+
- **`SCHEMA_VERSION` 升到 10** —— 字段搬了位置,而 schema-9 的 sanitizer 会按它知道的键重建每个图片条目:它既会丢掉这三个字段,也会继续读已经不存在的规则级值,于是一张被调暗的壁纸会静默回到 100%。
|
|
13
|
+
- **模糊的壁纸不再在视口四周画一圈黑边** —— `blur()` 把图层之外一律当作透明,于是边缘只有一半不透明,背后的页面透出来就是一道随模糊值变粗的暗边。现在每个图层的盒子向视口外各扩 2σ(由容器裁掉),取景位置同时补回同样的距离,画面不动。
|
|
14
|
+
- **透明度、亮度或模糊不同的两张图之间切换,现在真的会有动画** —— 每个壁纸图层记住的是**它正在画的那张图**的滤镜,壁纸自身的透明度则跟着过渡一起走,而不是在开始那一帧直接切成新值。此前两者都实时读当前图,等于 fade 还没跑,出去的图就已经换上新图的曝光了 —— 动画一直在,只是没有东西可动。
|
|
15
|
+
- **过渡中途重绘不会再把它掐断** —— 稳定后的透明度记在渲染层自己手里,而不是从 store 回读,所以主题重注册或面板重渲染时写回的是这次过渡要去的值,不是它离开的那个值。
|
|
16
|
+
- **拖动壁纸的透明度、亮度与模糊不再每帧整块重绘** —— 拖动只写壁纸层自己的那个属性,松手才走一次完整的 `setRule`(皮肤、调色板、壁纸一起)。此前拖动一帧就是一次全量重绘,图一大就明显卡。
|
|
17
|
+
- **滑块的预览与提交分开了** —— `onInput` 每帧只预览,提交改由原生 `change` 事件触发、一次落地;range 输入的 React `onChange` 本来就绑在同一个 `input` 事件上,所以按它提交等于按帧提交。
|
|
18
|
+
- **`setWpOpacity` / `setWpFilter` 又有人调用了** —— 这两个零延迟写入函数在合并滑块那一版之后一直没有调用者,而注释和 `check:image-mode` 仍按「两个站点」断言。`check:image-mode` 现在钉住面板真的接上了它们,以及预览只作用于正在生效的那条规则。
|
|
19
|
+
- **门禁** —— `check:node` 新增原子写与备份一节(坏文件不得覆盖好备份、临时文件不残留、清空连备份一起走、坏文件从备份恢复),并把「每张图三个效果」的抬升、上下限、缺省键与节日条目一起钉住;`check:image-mode` 钉住渲染层读的是**正在画的那张图**、面板写的是**正在编辑的那张图**、`defaultImage` 是所有创建点的唯一入口、模糊边缘取样到屏幕之外(2σ 扩幅,拖动那一帧也写),以及每个图层携带的是自己那张图的三个效果而不是实时读取。
|
|
20
|
+
|
|
21
|
+
## v0.9.2
|
|
22
|
+
|
|
23
|
+
- **「配置」页会报出有多少没人引用的图片,并把它们清掉** —— 图片按原图保存,所以一次被中断的上传、一次失败的文件删除或一次整批替换,都可能在磁盘上留下一个没有任何规则引用的 `modelbg-<slot>` 文件。这种残留天生不可见:启动只读配置里点名的槽位,所以孤儿文件从来不会被加载、被画出、也不会出现在任何地方。
|
|
24
|
+
- **先读、后删** —— 卡片先显示「可清理多少 MB / 几个文件」,然后才给出按钮;数字只描述这一按会释放什么(不是「正在使用多少」或总共几个文件 —— 后者会被读成「八个都要删」)。清理完重新读一次而不是用减法,所以没删掉的文件仍然算在里面,提示里也会点名是哪几个。
|
|
25
|
+
- **清理不问确认** —— 点一下就删。要删的文件按定义不被任何规则引用,而「确认」在这里只教人不看就点;安全性改放在**前置判断**上:配置读不出来时按钮是灰的。数字仍然是先读的 —— 先删后报数才是没人会同意的那个操作。
|
|
26
|
+
- **`modelbg-h-*` 可以被清掉** —— 那个槽位不属于任何配置(节日画在 `holiday-cache/`,槽位只读),所以这是唯一能删掉它的路径。`referencedSlots` 刻意只接**规则**,`check:store` 钉住调用点,免得以后的改动把节日条目加回去。
|
|
27
|
+
- **旧版宿主编译出来是「读不到」,不是「0 B」** —— node 半边新增两个方法(`storeUsage`、`pruneOrphans`),而对着旧 node 半边的浏览器半边会显示「重启 DSH」,而不是报一个没人量过的数字。
|
|
28
|
+
- **`check:store`** —— 两个判定(`referencedSlots` / `orphanSlots`)在纯 node 上跑:正在用的图永远不会是孤儿、`keep` 只可能**放过**槽位(上传的字节落地与命名它的规则条目之间的那段空隙)、以及客户端只送规则槽位。`check:node` 通过真实 RPC 处理器覆盖清理本身。
|
|
29
|
+
- **两份 README 追上校验的条数** —— 从 v0.8.1 的 `check:watchdogs` 与 `check:scheme` 起它们就一直写着「十道」;现在都列出来了,`check:store` 也在内。
|
|
4
30
|
|
|
5
31
|
## v0.9.1
|
|
6
32
|
|
package/README.md
CHANGED
|
@@ -9,7 +9,7 @@ English | [中文](README.zh.md)
|
|
|
9
9
|
|
|
10
10
|
> Forked from [`Tkingxiao/dsh-any-background`](https://github.com/Tkingxiao/dsh-any-background) and renamed to `dsh-background-by-model`.
|
|
11
11
|
|
|
12
|
-
A **DeepSeek Harness** appearance plugin built around an **ordered list of model rules**: each rule carries its own images,
|
|
12
|
+
A **DeepSeek Harness** appearance plugin built around an **ordered list of model rules**: each rule carries its own images, and each image its own layout mode, framing, theme color, opacity, brightness and blur. Switch the model and the background switches with it, through the global [switch effect](#switch-effect-global) you choose on the Config page.
|
|
13
13
|
|
|
14
14
|
> **v0.3.0 was a breaking release** — video wallpapers, generated backgrounds and the single global theme color were removed. See the [v0.3.0 entry in CHANGELOG.md](./CHANGELOG.md#v030).
|
|
15
15
|
|
|
@@ -61,7 +61,7 @@ One interface, one config — only the current model differs:
|
|
|
61
61
|
<p align="center">
|
|
62
62
|
<img src="https://cdn.jsdelivr.net/gh/HarmlessFunny/assets@v0.1.0/dsh-background-by-model/rule-editor.webp" alt="One rule's editor" width="660">
|
|
63
63
|
<br/>
|
|
64
|
-
<em>One rule on the Model Background tab · the
|
|
64
|
+
<em>One rule on the Model Background tab · the layout mode, the framing, the theme color and the opacity/brightness/blur all belong to the image being edited</em>
|
|
65
65
|
</p>
|
|
66
66
|
|
|
67
67
|
<p align="center">
|
|
@@ -74,7 +74,7 @@ One interface, one config — only the current model differs:
|
|
|
74
74
|
|
|
75
75
|
An ordered list of rules, matched first-hit against the current model's name, with rule 1 as the fallback.
|
|
76
76
|
|
|
77
|
-
- **Rules** — add, remove, reorder and name them; each carries its own match string,
|
|
77
|
+
- **Rules** — add, remove, reorder and name them; each carries its own match string, and a set of images with their own look.
|
|
78
78
|
- **Images per rule** — a filmstrip filled by file picker, drag & drop or a list of URLs; reorder it, promote one to first, or replace one in place (which keeps its position in the rotation). A rule may also hold none, and an empty rule still matches while it has a theme color of its own, so emptying one is a visible state rather than a trap.
|
|
79
79
|
- **Live match readout** — the Model Background tab shows which model was read and which rule it resolved to.
|
|
80
80
|
- **Import / export** — the whole rule set as `dsh-background-by-model-theme.json` with every image inlined; files written by earlier releases still import.
|
|
@@ -116,7 +116,7 @@ One switch on the Config page and nothing else: on 中秋节 and 国庆节 the w
|
|
|
116
116
|
- **Theme color** — HSL wheel, numeric input, **Extract from this image** and an eyedropper. It belongs to the **image**, and an image with none follows the system theme rather than inheriting its rule's.
|
|
117
117
|
- **Layout mode** — fit / fill / stretch / tile / center, stored per image; disabled on a rule that holds no picture, rather than hidden.
|
|
118
118
|
- **Framing** — drag to pan and scroll to zoom, editable in fit mode only, stored per image and stable across window resizes.
|
|
119
|
-
- **Image opacity** `0–100%`, **image brightness** `0–200%` (`100%` is the picture as saved) and **image blur** `0–60 px`, all three per
|
|
119
|
+
- **Image opacity** `0–100%`, **image brightness** `0–200%` (`100%` is the picture as saved) and **image blur** `0–60 px`, all three **saved per image** and edited through **one slider with a menu beside it** that picks the effect — so a daylight photo and a night shot in one rotation keep their own exposures. They treat the image (wallpaper) layer only; the Interface tab's opacity treats interface surfaces. A rule with no image has all three disabled rather than hidden.
|
|
120
120
|
|
|
121
121
|
### Global settings (Interface tab)
|
|
122
122
|
|
|
@@ -130,9 +130,21 @@ One click on the Config tab downloads the author's own configuration — rules,
|
|
|
130
130
|
|
|
131
131
|
- **Hosted in the store's own shape** (`preset/preset.json`, `preset/theme-config.json`, one `modelbg-<slot>` file per wallpaper), so it stays editable on GitHub and publishing it is a `cp`.
|
|
132
132
|
- **Every interface number in it is what the plugin already ships with**, so on a new install the button adds rules and pictures; on a store you have already tuned it resets those too, because it is a whole configuration and not a patch.
|
|
133
|
-
- **The download comes before the question**, so the confirmation can say what is actually in hand — and the wipe comes after the download, never before it. It is the only
|
|
133
|
+
- **The download comes before the question**, so the confirmation can say what is actually in hand — and the wipe comes after the download, never before it. It is the only card in the panel that **asks before it deletes**.
|
|
134
134
|
- **One missing wallpaper fails the whole attempt and names the slot**, and every file retries on its own, keeping what arrived for the next press.
|
|
135
135
|
|
|
136
|
+
### Image storage cleanup
|
|
137
|
+
|
|
138
|
+
The last card on the Config tab. Images are stored at **full fidelity**, so an interrupted upload, a failed file deletion or a wholesale config replacement can leave a file on disk that no rule references any more — and on a tidy machine that number is normally **0**. The card reads the numbers, and the button deletes **without asking**.
|
|
139
|
+
|
|
140
|
+
- **Read first, delete second** — it shows how much is cleanable and how many files that is, before it offers the button. A cleanup whose size is announced afterwards is a cleanup nobody agrees to. The numbers describe only **what the press would free**: "2.1 MB in use" answers a question nobody asked on this card, and a total file count reads as "eight to delete" when the honest answer is one.
|
|
141
|
+
- **Only unreferenced files** — every byte a current rule uses is untouched, and the config itself is never written. The card re-reads after the sweep instead of subtracting, so a file that failed to delete still counts.
|
|
142
|
+
- **Failures are named** — one undeletable file does not protect the other six, and it is not reported as success either: the toast lists which ones.
|
|
143
|
+
- **No confirmation step** — what it deletes is by definition referenced by no rule, and is not a choice made from a working set, so a "confirm?" here only teaches people to click through. The safety is in the **gate**: when the config cannot be read the button is disabled (next bullet), rather than seven files being listed and then asked about.
|
|
144
|
+
- **A corrupt live file is answered by the backup** — when the live config will not parse but the `.bak` does, the sweep runs against the **backup's** rules, because that is the config you are about to get back; only when neither parses does it read as unknown and disable the button.
|
|
145
|
+
- **It also clears a stray `modelbg-h-*`** — that slot belongs to no config (festival art lives in `holiday-cache/`, and the slot is read-only), so this is the only path that can ever remove such a file.
|
|
146
|
+
- **An older host reads as "unknown", not "0 B"** — the two nothings must not look the same.
|
|
147
|
+
|
|
136
148
|
## Settings
|
|
137
149
|
|
|
138
150
|
Settings → **Theme** now has three tabs:
|
|
@@ -141,7 +153,7 @@ Settings → **Theme** now has three tabs:
|
|
|
141
153
|
| --- | --- | --- |
|
|
142
154
|
| **Interface** | Global, shared by every model | Opacity for the main background, left panel, right panel, cards & panels, input & controls, settings panel, conversation text box, trajectory page and every plugin page |
|
|
143
155
|
| **Model Background** | Per rule, per image | The ordered rule list, the live match readout, and each rule's images (filmstrip), **per-image layout mode, framing and theme color**, plus the rule's opacity, brightness, blur and [rotation](#image-rotation) |
|
|
144
|
-
| **Config** | — | The global [switch effect](#switch-effect-global), the whole rule set as a file — [recommended profile](#recommended-profile), import and export (`dsh-background-by-model-theme.json`) — plus the single [holiday background](#holiday-backgrounds) switch |
|
|
156
|
+
| **Config** | — | The global [switch effect](#switch-effect-global), the whole rule set as a file — [recommended profile](#recommended-profile), import and export (`dsh-background-by-model-theme.json`) — plus the single [holiday background](#holiday-backgrounds) switch and the [image storage cleanup](#image-storage-cleanup) |
|
|
145
157
|
|
|
146
158
|
The old **Color** tab is gone — the theme color is now a property of each rule — and the old **Background** tab became **Model Background**.
|
|
147
159
|
|
|
@@ -151,7 +163,8 @@ Data directory: `~/.dsh/.dsh-background-by-model-data/` (Windows: `C:\Users\<you
|
|
|
151
163
|
|
|
152
164
|
| File | Contents |
|
|
153
165
|
| --- | --- |
|
|
154
|
-
| `theme-config.json` | The rule list (each rule with its image list and rotation) plus the global Interface settings, the global switch effect and the holiday overrides |
|
|
166
|
+
| `theme-config.json` | The rule list (each rule with its image list, and each image with its own look and rotation settings) plus the global Interface settings, the global switch effect and the holiday overrides |
|
|
167
|
+
| `theme-config.json.bak` | The previous config, as of the last **successful** save. Every save writes a temp file and renames it over the live one, rotating the current good file into `.bak` first; a live file that will not parse is restored from here instead of falling back to the factory defaults. With neither readable, the cleanup card refuses to delete images |
|
|
155
168
|
| `modelbg-<slot>` | One image, stored as raw bytes without a file extension — one file per image, so a rule with three images owns three slots |
|
|
156
169
|
| `holiday-cache/<tag>/<asset>` | Festival art downloaded from the CDN, one file per holiday (`mid-autumn.webp`, `national-day.webp`) inside a directory named after the assets release this build pins (`v0.1.0`). The tag is part of the path so that a build pinning a new tag starts from an empty directory instead of being answered with the previous generation's bytes; the file inside is named after the **asset**, deliberately outside the slot namespace, which is what keeps a holiday slot read-only. Superseded generations are pruned once the new art is on disk. Delete a file here and it is simply re-downloaded the next time that holiday is in force |
|
|
157
170
|
|
|
@@ -184,7 +197,7 @@ npx @deepseek-ai/dsh web
|
|
|
184
197
|
git clone https://github.com/HarmlessFunny/dsh-background-by-model.git
|
|
185
198
|
cd dsh-background-by-model
|
|
186
199
|
pnpm install
|
|
187
|
-
pnpm test # builds lib/, typechecks, runs the
|
|
200
|
+
pnpm test # builds lib/, typechecks, runs the thirteen checks
|
|
188
201
|
```
|
|
189
202
|
|
|
190
203
|
`pnpm run bundle` rebuilds `lib/` on its own. Either has to run before the plugin can load: a fresh clone has no `lib/`.
|
|
@@ -206,18 +219,21 @@ To mount a working copy into a profile instead, add it to the profile's `package
|
|
|
206
219
|
|
|
207
220
|
After changing anything under `src/`, run `pnpm run bundle` again — the mounted profile loads `lib/`, so edits do not take effect until the bundle is rebuilt.
|
|
208
221
|
|
|
209
|
-
`pnpm test` builds, typechecks and runs
|
|
222
|
+
`pnpm test` builds, typechecks and runs thirteen checks, none of which needs a dependency, a transformer or a browser. Each can also be run on its own with `pnpm check:holiday` / `pnpm check:rotation` / `pnpm check:transition` / `pnpm check:repaint` / `pnpm check:code-plate` / `pnpm check:image-mode` / `pnpm check:rules` / `pnpm check:preset` / `pnpm check:ui` / `pnpm check:watchdogs` / `pnpm check:scheme` / `pnpm check:store` / `pnpm check:node`:
|
|
210
223
|
|
|
211
224
|
- **`check:holiday`** — the two holiday windows, the Beijing day boundary, leap eighth months across 1900–2100, and the four gates `pickHoliday` applies.
|
|
212
225
|
- **`check:rotation`** — `nextIndex` / `isRotating`: no walking off the end, shuffle never repeating the image on screen, and nothing called "rotating" with nothing to rotate.
|
|
213
226
|
- **`check:transition`** — `resolveFadeMs` / `transitionPlan`: the shipped default still producing byte-for-byte the transition string earlier releases wrote, every route to a hard cut being one, reduced motion vetoing rather than shortening, and every effect ending visible and unscaled.
|
|
214
227
|
- **`check:repaint`** — `shouldRepaint`, including the edit that **creates** the winner, plus a failure if any write path stops asking, or if a rotation step stops re-emitting the interface palette.
|
|
215
228
|
- **`check:code-plate`** — the code block's plate: its tokens declared on both `:root` and `body`, the light branch emitting the banner, and each surface reading its own plugin variable.
|
|
216
|
-
- **`check:image-mode`** — the layout mode
|
|
229
|
+
- **`check:image-mode`** — the lift onto the image for the layout mode and the three paint effects, and which image a control edits against which the render layer reads.
|
|
217
230
|
- **`check:rules`** — the two decisions behind the tab strip, which live in `src/client/rules-view.ts`, plus the page structure the layout rests on.
|
|
218
231
|
- **`check:preset`** — the recommended profile's retry policy and what a failed attempt holds for the next one, with both halves shown using them.
|
|
219
232
|
- **`check:ui`** — both dictionaries carrying the same keys, every `dab-…` class styled, no dead entry, and every `var(--dsw-…)` published by the installed theme.
|
|
220
|
-
- **`check:
|
|
233
|
+
- **`check:watchdogs`** — one heartbeat, entries firing on their own due time, paused while the tab is hidden, no timer left by dispose, and no module outside the entry starting its own interval.
|
|
234
|
+
- **`check:scheme`** — the `data-ds-dark-theme` hand-off: the plugin only rewrites the value it wrote, hands the flag back when it drops its tokens, and repaints when the scheme moves.
|
|
235
|
+
- **`check:store`** — the two decisions behind the storage cleanup, `referencedSlots` and `orphanSlots`: a picture in use is never an orphan, a stray holiday-slot file always is, and the browser half sends RULE slots rather than the whole config.
|
|
236
|
+
- **`check:node`** — the built node half through its real RPC handler with `DSH_HOME` redirected and `fetch` stubbed: the holiday block, the festival art's caching and pruning, mirror fallback, the per-image color AND effect lifts, the global switch effect, the atomic config write with its backup and its recovery, the store's usage report and cleanup, and the recommended profile end to end.
|
|
221
237
|
|
|
222
238
|
## FAQ
|
|
223
239
|
|
|
@@ -228,7 +244,10 @@ Rule 1 probably has an empty match string, which makes it a pure fallback holdin
|
|
|
228
244
|
Matching is first-hit, not best-hit: put the more specific rule higher in the list, or reorder.
|
|
229
245
|
|
|
230
246
|
**Where are my wallpapers?**
|
|
231
|
-
In `~/.dsh/.dsh-background-by-model-data/`, one `modelbg-<slot>` file per image plus `theme-config.json`.
|
|
247
|
+
In `~/.dsh/.dsh-background-by-model-data/`, one `modelbg-<slot>` file per image plus `theme-config.json` and its `.bak` backup.
|
|
248
|
+
|
|
249
|
+
**What is `theme-config.json.bak`, and can I delete it?**
|
|
250
|
+
The previous config as of the last **successful** save. Every save writes a temp file and renames it over the live one, keeping the then-current parseable file as the backup — so if the live file ever stops parsing (a crash, a pulled cable, a hand edit gone wrong), the plugin restores from it instead of falling back to the factory defaults. You can delete it; the cost is having nothing to restore the next time the live file really is broken.
|
|
232
251
|
|
|
233
252
|
**I turned the rotation on and the background never changed.**
|
|
234
253
|
Three things can hold it: the rule needs two or more images, the tab has to be visible, and only the rule the current model resolved to rotates.
|
|
@@ -270,16 +289,19 @@ The effect is **Instant**, or the duration is `0` — an effect and a duration a
|
|
|
270
289
|
|
|
271
290
|
> Only the two most recent releases are listed here; older ones live in [CHANGELOG.md](./CHANGELOG.md).
|
|
272
291
|
|
|
273
|
-
### v0.
|
|
292
|
+
### v0.10.0
|
|
274
293
|
|
|
275
|
-
- **The
|
|
294
|
+
- **The config is written atomically, with a `.bak` of the last good file** — a save writes a temp file and renames it over the live one, keeping the previous parseable file as the backup; a corrupt live file is restored from it instead of falling back to the factory defaults and then being overwritten by your next drag.
|
|
295
|
+
- **Opacity, brightness and blur are saved per image** — the same layer as the layout mode, framing and theme color; a schema-9 config's rule-level values are lifted onto every image on read, so nothing changes on screen.
|
|
296
|
+
- **`SCHEMA_VERSION` is 10** — the fields moved, and an older host would drop them in silence, so the browser half has to know.
|
|
297
|
+
- **A blurred wallpaper no longer paints a dark rim around the viewport** — the layer's box is grown 2σ past the screen edge and clipped, with the framing moved back by the same amount, so the blur samples off screen instead of fading into the page behind it.
|
|
298
|
+
- **A switch between two different opacity, brightness or blur values animates now** — each layer keeps its own picture's filter, and the wallpaper's opacity rides the transition instead of snapping.
|
|
299
|
+
- **Dragging one of the three sliders no longer repaints everything per frame** — a drag frame writes only that field's property, and one full repaint lands when the gesture ends.
|
|
276
300
|
|
|
277
|
-
### v0.9.
|
|
301
|
+
### v0.9.2
|
|
278
302
|
|
|
279
|
-
- **The
|
|
280
|
-
-
|
|
281
|
-
- **The browser entry point is wiring again** — skin, watchdogs, rotation, boot, model state, extraction and theme files are their own modules.
|
|
282
|
-
- **Exporting a theme no longer cancels its own download**, and comments say why the code is what it is rather than what it used to be.
|
|
303
|
+
- **The Config tab gains an "Image storage" card** — it reports how much is cleanable and how many files that is, then offers the button; only unreferenced files go, the config and the festival art stay, and any file that resists is named.
|
|
304
|
+
- **`check:store`, so there are thirteen checks now** — both READMEs had been claiming ten, having missed `check:watchdogs` and `check:scheme` since v0.8.1; they are listed again alongside the new one.
|
|
283
305
|
|
|
284
306
|
## Star History
|
|
285
307
|
[](https://www.star-history.com/?repos=HarmlessFunny%2Fdsh-background-by-model&type=timeline&legend=bottom-right)
|
package/README.zh.md
CHANGED
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
|
|
10
10
|
> 派生自 [`Tkingxiao/dsh-any-background`](https://github.com/Tkingxiao/dsh-any-background),并重命名为 `dsh-background-by-model`。
|
|
11
11
|
|
|
12
|
-
一个 **DeepSeek Harness**
|
|
12
|
+
一个 **DeepSeek Harness** 外观插件,核心是一份**有序的模型规则列表**:每条规则自带壁纸(可多张),**每张图各有自己的布局模式、取景、主题色,以及透明度、亮度与模糊度**。切换模型即切换背景,切换过程走你在「配置」页选定的全局[切换效果](#切换效果全局)。
|
|
13
13
|
|
|
14
14
|
> **v0.3.0 是破坏性更新** —— 视频背景、生成式背景与全局主题色均已被移除。详见 [CHANGELOG.zh.md 的 v0.3.0 条目](./CHANGELOG.zh.md#v030)。
|
|
15
15
|
|
|
@@ -61,7 +61,7 @@
|
|
|
61
61
|
<p align="center">
|
|
62
62
|
<img src="https://cdn.jsdelivr.net/gh/HarmlessFunny/assets@v0.1.0/dsh-background-by-model/rule-editor.webp" alt="单条规则的编辑器" width="660">
|
|
63
63
|
<br/>
|
|
64
|
-
<em>「模型背景」页的单条规则 ·
|
|
64
|
+
<em>「模型背景」页的单条规则 · 布局模式、取景、主题色与透明度/亮度/模糊,全都属于它正在编辑的那张图</em>
|
|
65
65
|
</p>
|
|
66
66
|
|
|
67
67
|
<p align="center">
|
|
@@ -74,7 +74,7 @@
|
|
|
74
74
|
|
|
75
75
|
一份有序的规则列表,按当前模型名先命中者胜,第 1 条兼任兜底。
|
|
76
76
|
|
|
77
|
-
- **规则** ——
|
|
77
|
+
- **规则** —— 增删、排序、命名;每条自带一个匹配串,以及一组图片与它们各自的外观。
|
|
78
78
|
- **每条规则多张图** —— 胶片条可用文件选择、拖放或一行一个网址填入;可排序、设为第一张、或原地替换(替换会保住它在轮换里的位置)。规则也可以一张图都没有,而只要它还有自己的主题色,空规则依旧参与匹配,所以「清空」是一个看得见的状态,而不是一个陷阱。
|
|
79
79
|
- **实时匹配状态** —— 「模型背景」页会显示读到的是哪个模型、落在哪条规则上。
|
|
80
80
|
- **导入 / 导出** —— 整套规则导出为 `dsh-background-by-model-theme.json`,图片全部内联;旧版本写出的文件仍可导入。
|
|
@@ -110,13 +110,13 @@
|
|
|
110
110
|
- **画是下载的,不随包发布** —— 每个节日一张压缩后的壁纸,钉在项目 [assets 仓库](https://github.com/HarmlessFunny/assets)的一个发行 tag 上,当天第一次读取时缓存到 `holiday-cache/<tag>/`。下载由日历把关,所以平常的日子一个字节都不取,此后的每一次启动都直接读盘。
|
|
111
111
|
- **画和它的配色都不可以换** —— 节日槽位只读,颜色与满幅的「填充」都取自定义,主题导出也只带你的规则。
|
|
112
112
|
|
|
113
|
-
###
|
|
113
|
+
### 每条规则与每张图各自的设置
|
|
114
114
|
|
|
115
115
|
- **壁纸** —— 每条规则一张或多张图;不轮换时规则画的是第一张。
|
|
116
116
|
- **主题色** —— HSL 色轮、数值输入、**从本图提取**与吸管。它属于**图片**,没有自己颜色的图跟随系统主题,而不是继承规则色。
|
|
117
117
|
- **布局模式** —— 适应 / 填充 / 拉伸 / 平铺 / 居中,逐图保存;规则没有图片时这排是禁用而不是隐藏。
|
|
118
118
|
- **取景** —— 拖动平移、滚轮缩放,只在适应模式下可编辑,逐图保存,窗口缩放后保持一致。
|
|
119
|
-
- **图片透明度** `0–100%`、**图片亮度** `0–200%`(`100%` 即原图)与**图片模糊** `0–60 px
|
|
119
|
+
- **图片透明度** `0–100%`、**图片亮度** `0–200%`(`100%` 即原图)与**图片模糊** `0–60 px`,三者都**逐图保存**,并通过**同一条滑块 + 旁边的下拉框**切换调节项 —— 一张亮图和一张夜景图因此在同一组轮换里各有各的曝光。它们只作用于图片层;「界面」页的透明度作用于界面各区域。没有任何图片的规则这三项是禁用而不是隐藏。
|
|
120
120
|
|
|
121
121
|
### 全局设置(「界面」页)
|
|
122
122
|
|
|
@@ -130,9 +130,21 @@
|
|
|
130
130
|
|
|
131
131
|
- **托管在数据目录自己的形状里**(`preset/preset.json`、`preset/theme-config.json`,每张壁纸一个 `modelbg-<slot>` 文件),所以它能在 GitHub 上直接编辑,发布它就是一次 `cp`。
|
|
132
132
|
- **里面每一个界面数字都是插件本来就用着的值**,所以在新装上是「加上规则和图片」;而在你已经调过的数据目录上,它把这些也一起重置 —— 它是一整份配置,不是一个补丁。
|
|
133
|
-
- **先下载、后提问**,所以确认框能如实说出手里有什么 ——
|
|
133
|
+
- **先下载、后提问**,所以确认框能如实说出手里有什么 —— 而清空在下载**之后**,绝不在之前。它是面板里唯一一张会**先问再删**的卡片。
|
|
134
134
|
- **少一张壁纸就整体失败并报出是哪个槽位**,而且每个文件各自重试,已经下到的部分留给下一次。
|
|
135
135
|
|
|
136
|
+
### 图片存储清理
|
|
137
|
+
|
|
138
|
+
「配置」页最后一张卡片:图片是按**原图**保存的,所以一次被中断的上传、一次失败的文件删除,或一次整套配置的替换,都可能在磁盘上留下不再被任何规则引用的文件 —— 而这台机器上「孤儿」正常是 **0**。卡片把用量读出来,**点清理就直接删**。
|
|
139
|
+
|
|
140
|
+
- **先读、后删** —— 卡片先显示「可清理多少 MB / 几个文件」,再给出清理按钮;先删再报数的操作没人会同意。数字只描述**这一按会释放什么**:显示「正在使用 2.1 MB」是在回答一个没人问的问题,而显示「8 个文件」会让人以为八张全要删掉。
|
|
141
|
+
- **只删没人引用的** —— 当前规则用到的图一个字节都不动,配置本身也不写。清理完会重新读一次,而不是用减法算,所以删除失败的文件仍然算在里面。
|
|
142
|
+
- **失败会点名** —— 一个文件删不掉不会让其余六个留下来,但也不会被说成「已清理」:提示里会列出是哪几个。
|
|
143
|
+
- **不问确认** —— 要删的东西按定义没有任何规则引用,而且不是从一个能用的集合里挑出来的,所以「确认」在这里只教人不看就点。安全性放在**前置判断**上:配置读不出来时按钮是灰的(见下一条),而不是先把七个文件列出来再问一遍。
|
|
144
|
+
- **坏掉的主文件由备份作答** —— 主配置读不出来、而 `.bak` 能解析时,清理按**备份里的规则**走:那正是你马上会拿回的配置。两份都读不出来才是「读不到」,按钮这时候才是灰的。
|
|
145
|
+
- **顺手清掉误入槽位的节日文件** —— `modelbg-h-*` 不属于任何配置(节日画在 `holiday-cache/` 里,那个槽位只读),所以它是唯一一个只有这条路径能清掉的残留。
|
|
146
|
+
- **宿主是旧版时显示「读不到」而不是「0 B」** —— 两种「没有」必须长得不一样。
|
|
147
|
+
|
|
136
148
|
## 设置界面
|
|
137
149
|
|
|
138
150
|
设置的**「主题」**分类下现在有三个选项卡:
|
|
@@ -141,7 +153,7 @@
|
|
|
141
153
|
| --- | --- | --- |
|
|
142
154
|
| **界面** | 全局,所有模型共用 | 主背景、左侧栏、右侧栏、卡片面板、输入框与控件、设置面板、对话文本框、轨迹页与每一个插件页的透明度 |
|
|
143
155
|
| **模型背景** | 每条规则、每张图片 | 有序规则列表、实时匹配状态,以及每条规则的图片(胶片条)、**逐图布局模式 / 取景 / 主题色**,加上规则自己的透明度、亮度、模糊度与[多图轮换](#多图轮换) |
|
|
144
|
-
| **配置** | — | 全局[切换效果](#切换效果全局)、整套规则的进出 —— [推荐配置](#推荐配置)与导入 / 导出(`dsh-background-by-model-theme.json`)—— 外加[节日特殊背景](#节日特殊背景)
|
|
156
|
+
| **配置** | — | 全局[切换效果](#切换效果全局)、整套规则的进出 —— [推荐配置](#推荐配置)与导入 / 导出(`dsh-background-by-model-theme.json`)—— 外加[节日特殊背景](#节日特殊背景)那一个开关,以及[图片存储清理](#图片存储清理) |
|
|
145
157
|
|
|
146
158
|
原先的**「色彩」**选项卡已删除 —— 主题色改为规则与图片各自的属性 —— 原**「背景」**选项卡改造成**「模型背景」**。
|
|
147
159
|
|
|
@@ -151,7 +163,8 @@
|
|
|
151
163
|
|
|
152
164
|
| 文件 | 内容 |
|
|
153
165
|
| --- | --- |
|
|
154
|
-
| `theme-config.json` |
|
|
166
|
+
| `theme-config.json` | 规则列表(每条规则含图片列表,每张图含自己的外观与轮换设置)+ 全局「界面」设置 + 全局切换效果 + 节日覆盖配置 |
|
|
167
|
+
| `theme-config.json.bak` | 上一份**写成功时**的配置。每次保存都是「先写临时文件、再改名覆盖」,并在覆盖前把当前这份合格的文件留成 `.bak`;主文件读不出来时就从这里恢复,而不是退回出厂默认。读不出且没有备份时,清理卡会拒绝删图 |
|
|
155
168
|
| `modelbg-<slot>` | 一张图片,保存为原始字节、无扩展名 —— 一张图一个文件,所以一条有三张图的规则占三个槽位 |
|
|
156
169
|
| `holiday-cache/<tag>/<asset>` | 从 CDN 下载的节日画,一个节日一个文件(`mid-autumn.webp`、`national-day.webp`),装在一个以**插件所钉的 assets 发行版**命名的目录里(`v0.1.0`)。tag 进了路径,所以钉了新 tag 的构建从一个空目录开始,而不是被告知上一代的字节就是答案;目录里的文件名仍然是**素材名**,刻意放在槽位命名空间之外,这正是节日槽位只读的原因。被取代的旧代会在新图落盘之后被清掉。删掉这里的文件也没关系,下次那个节日生效时会重新下载 |
|
|
157
170
|
|
|
@@ -184,7 +197,7 @@ npx @deepseek-ai/dsh web
|
|
|
184
197
|
git clone https://github.com/HarmlessFunny/dsh-background-by-model.git
|
|
185
198
|
cd dsh-background-by-model
|
|
186
199
|
pnpm install
|
|
187
|
-
pnpm test # 构建 lib
|
|
200
|
+
pnpm test # 构建 lib/、类型检查、跑十三道检查
|
|
188
201
|
```
|
|
189
202
|
|
|
190
203
|
`pnpm run bundle` 只重建 `lib/`。两者都必须在插件能加载之前先跑一次:新 clone 出来没有 `lib/`。
|
|
@@ -206,18 +219,21 @@ pnpm test # 构建 lib/、类型检查、跑十道检查
|
|
|
206
219
|
|
|
207
220
|
改完 `src/` 必须重新执行 `pnpm run bundle` 才会生效 —— 挂载的 profile 加载的是 `lib/`。
|
|
208
221
|
|
|
209
|
-
`pnpm test`
|
|
222
|
+
`pnpm test` 会构建、类型检查并跑十三道校验,十三道都不需要依赖、不需要转译器、也不需要浏览器。也可以单独跑:`pnpm check:holiday` / `pnpm check:rotation` / `pnpm check:transition` / `pnpm check:repaint` / `pnpm check:code-plate` / `pnpm check:image-mode` / `pnpm check:rules` / `pnpm check:preset` / `pnpm check:ui` / `pnpm check:watchdogs` / `pnpm check:scheme` / `pnpm check:store` / `pnpm check:node`:
|
|
210
223
|
|
|
211
224
|
- **`check:holiday`** —— 两个节日窗口、北京时间的跨日边界、1900–2100 年间的闰八月,以及 `pickHoliday` 的四道闸门。
|
|
212
225
|
- **`check:rotation`** —— `nextIndex` / `isRotating`:不走越界、随机不重复当前这张、没有可轮换的东西时绝不报「正在轮换」。
|
|
213
226
|
- **`check:transition`** —— `resolveFadeMs` / `transitionPlan`:出厂默认仍然产出与旧版本逐字节相同的过渡串、每一条硬切路径都确实是硬切、「减少动态效果」是否决而非缩短,以及每种效果结束时都完全可见且没有残留缩放。
|
|
214
227
|
- **`check:repaint`** —— `shouldRepaint`,包括那条**制造**赢家的编辑,以及任何一条写入路径不再询问、或轮换步骤不再重发界面调色板时报错。
|
|
215
228
|
- **`check:code-plate`** —— 代码块底板:token 在 `:root` 与 `body` 上都有声明、浅色分支发出 banner、两块表面各读自己的插件变量。
|
|
216
|
-
- **`check:image-mode`** ——
|
|
229
|
+
- **`check:image-mode`** —— 布局模式与三个壁纸效果放到图片上的那次抬升,以及某个控件编辑的是哪张图、渲染层读的又是哪张图。
|
|
217
230
|
- **`check:rules`** —— 选项卡背后那两个住在 `src/client/rules-view.ts` 的判定,以及布局所依赖的页面结构。
|
|
218
231
|
- **`check:preset`** —— 推荐配置的重试策略与失败那一次给下一次留下什么,并验证两侧真的在用它们。
|
|
219
232
|
- **`check:ui`** —— 两本字典键集一致、每个 `dab-…` 类都有样式、没有死键,以及每个 `var(--dsw-…)` 都是已安装主题发布过的 token。
|
|
220
|
-
- **`check:
|
|
233
|
+
- **`check:watchdogs`** —— 一条心跳、按各自到期时间触发、隐藏即暂停、dispose 不留定时器,且入口之外没有模块自己起 interval。
|
|
234
|
+
- **`check:scheme`** —— `data-ds-dark-theme` 的交接:插件只改自己写的那个值、清掉 token 时一起交还标记、方案变了会重绘。
|
|
235
|
+
- **`check:store`** —— 存储清理的两个判定:`referencedSlots` 与 `orphanSlots`。钉住「正在用的图不会被当成孤儿」与「节日槽位的文件必须可清」,外加浏览器半边传的是**规则槽位**而不是整份配置。
|
|
236
|
+
- **`check:node`** —— 把构建好的 node 半边通过真实的 RPC 处理器跑一遍(`DSH_HOME` 指向临时目录、`fetch` 换成桩):节日配置块、节日画的缓存与清理、镜像回落、逐图颜色与逐图效果的抬升、全局切换效果、配置的原子写与备份/恢复、图片存储的用量报告与清理,以及推荐配置的整条链路。
|
|
221
237
|
|
|
222
238
|
## 常见问题
|
|
223
239
|
|
|
@@ -228,7 +244,10 @@ pnpm test # 构建 lib/、类型检查、跑十道检查
|
|
|
228
244
|
匹配是先命中者胜,而不是最精确者胜:把更具体的规则往上拖,或调整顺序。
|
|
229
245
|
|
|
230
246
|
**图片存在哪?**
|
|
231
|
-
在 `~/.dsh/.dsh-background-by-model-data/`:每张图一个 `modelbg-<slot>` 文件,外加 `theme-config.json
|
|
247
|
+
在 `~/.dsh/.dsh-background-by-model-data/`:每张图一个 `modelbg-<slot>` 文件,外加 `theme-config.json` 与它的 `.bak` 备份。
|
|
248
|
+
|
|
249
|
+
**`theme-config.json.bak` 是什么?可以删吗?**
|
|
250
|
+
是上一份**成功保存**的配置。每次保存都先写临时文件再改名覆盖,覆盖前把当时那份能解析的文件留成备份,所以主文件哪天读不出来(断电、崩溃、手滑编辑),插件会从备份恢复而不是退回出厂默认。可以删,代价是下次真的坏掉时就没有可恢复的那一份。
|
|
232
251
|
|
|
233
252
|
**我开了轮换,背景却一直没变。**
|
|
234
253
|
有三件事会拦住它:规则至少要有两张图;标签页必须可见;只有当前模型解析出的那条规则在轮换。
|
|
@@ -270,16 +289,19 @@ pnpm test # 构建 lib/、类型检查、跑十道检查
|
|
|
270
289
|
|
|
271
290
|
> 这里只列最近两个版本;更早的版本见 [CHANGELOG.zh.md](./CHANGELOG.zh.md)。
|
|
272
291
|
|
|
273
|
-
### v0.
|
|
292
|
+
### v0.10.0
|
|
274
293
|
|
|
275
|
-
-
|
|
294
|
+
- **配置改成原子写,并留一份 `.bak`** —— 保存先写临时文件再改名覆盖,覆盖前把当前能解析的那份留成备份;主文件坏了就从备份恢复,而不是退回出厂默认、再被你下一次拖动覆盖掉。
|
|
295
|
+
- **透明度、亮度与模糊改成逐图保存** —— 与布局模式、取景、主题色同一层;schema-9 的规则级三个值读取时抬到每张图上,升级不改屏幕。
|
|
296
|
+
- **`SCHEMA_VERSION` 升到 10** —— 字段搬了位置,旧宿主会静默丢掉它们,所以必须让浏览器半边知道。
|
|
297
|
+
- **模糊的壁纸不再在视口四周画一圈黑边** —— 图层盒子向屏幕外各扩 2σ 再裁掉,取景位置补回同样的距离,模糊因此取样到屏幕之外,边缘不再透出背后页面的颜色。
|
|
298
|
+
- **透明度、亮度或模糊不同的两张图之间切换现在有动画了** —— 每个图层记住自己那张图的滤镜,壁纸透明度也跟着过渡走,不再直接切。
|
|
299
|
+
- **拖动这三个滑块不再每帧整块重绘** —— 拖动只写那个字段自己的属性,松手才走一次完整重绘。
|
|
276
300
|
|
|
277
|
-
### v0.9.
|
|
301
|
+
### v0.9.2
|
|
278
302
|
|
|
279
|
-
-
|
|
280
|
-
-
|
|
281
|
-
- **浏览器半边入口只剩接线** —— 皮肤、看守、轮换、启动、模型状态、取色与主题文件各自成模块。
|
|
282
|
-
- **导出主题不再取消自己的下载**,注释也只讲代码为什么是现在这样、不讲它曾经是什么样。
|
|
303
|
+
- **「配置」页多了一张「图片存储」卡片** —— 先报出可清理多少、涉及几个文件,再给你一个清理按钮;只删没有规则引用的文件,配置与节日画都不动,删不掉的文件会点名。
|
|
304
|
+
- **`check:store`,于是现在十三道校验** —— 两份 README 此前一直写着「十道」,`check:watchdogs` 与 `check:scheme` 从 v0.8.1 起就没列进去,这次一并补上。
|
|
283
305
|
|
|
284
306
|
## Star History
|
|
285
307
|
|