Voyage-He/dsh-background-image

dsh-background-image

deepseek harness background-image plugin, built by DS and GPT

未分類dshdsh-plugins

dsh-plugin-background-image

English | 简体中文

A background image plugin for DeepSeek Harness (DSH), for both the Web UI and the Desktop app: set a web image, local image, or preset gradient as the interface background, with image opacity, display scope, frosted-glass blur, per-region opacity, and chat-content offset for a more immersive interface.

Adapted to DSH 0.2.1+ (the modern Settings / Plugin Manager slots) and to DeepSeek Harness Desktop.

Features

  • Web images (http(s)://), local images (absolute paths), and data:image/ data URLs
  • Desktop-aware local images: in the Desktop app the native file dialog returns the real absolute path through the preload bridge; in a browser the plugin's host route opens the system dialog instead
  • Local image invalidation hint: the referenced local file is probed automatically on page load and whenever the settings page opens; if it has been moved or deleted, a prominent hint asks you to re-pick it
  • Preset gradient palettes (Aurora / Sky / Sakura / Sunset / Mint / Ocean)
  • Image opacity adjustment
  • Display scope: Immersive fullscreen / Conversation area only
  • Frosted-glass blur + color saturation (applied to the sidebar and glass panels such as the composer card)
  • Conversation frosted glass: independent blur (0–48 px) and opacity (0–100%) in both display modes; defaults to transparent with no blur to preserve existing settings
  • Readability protection: the glass dims the image behind it in dark themes and brightens it in light themes, so sidebar labels and conversation text stay legible over very bright or very dark wallpapers
  • Per-region opacity: sidebar, conversation area, and composer can be tuned independently (the sidebar only takes effect in immersive fullscreen)
  • Chat content offset: shift the chat content (message list + composer card, ±320px, column width unchanged) left or right while the header stays in place, to better showcase the background
  • Clean disable: turning the plugin off removes every theme-token and internal-style override, fully restoring the native DSH look
  • Settings are part of the plugin's own Config and are persisted by the DSH settings system in the profile patch; they survive a page refresh or a DSH restart

Demo

DSH background image plugin demo DSH background image plugin demo DSH background image plugin demo

Installation

In the Desktop app

Open the Plugins panel from the sidebar's panel list, then add the plugin from the local directory or from npm. The Desktop app uses the desktop profile, for example:

npx @deepseek-ai/dsh plugin --profile desktop add \
  dsh-plugin-background-image@file:/path/to/background-image-plugin

From a local directory (Web UI)

npx @deepseek-ai/dsh plugin --profile <profile> add \
  dsh-plugin-background-image@file:/path/to/background-image-plugin

For example:

npx @deepseek-ai/dsh plugin --profile web add \
  dsh-plugin-background-image@file:/Users/your-name/projects/background-image-plugin

When the Plugin Manager installs a directory as a link (link:… in the profile's package.json), run pnpm install once inside that directory so the plugin can resolve its @deepseek-ai/schemastery dependency; otherwise the Host reports ERR_MODULE_NOT_FOUND and the plugin stays inactive. Installing the published package from npm installs the dependency automatically.

From npm

npx @deepseek-ai/dsh plugin --profile <profile> add dsh-plugin-background-image

Start DSH with the same profile after installation and the plugin will load. Installing a new bundle can activate through HMR; replacing an already installed package requires a restart.

Usage

  1. Open DSH.
  2. Go to Settings → Background Image (a top-level tab in the settings sidebar). Alternatively, open the Plugins panel from the sidebar's panel list, open the Background Image bundle card under Installed, and click Configure on the plugin's row.
  3. Enable the background, then choose a web image, a local image, or a preset gradient. For local images, clicking "Choose Local Image" opens the native system file dialog; the selected absolute path is recorded (the file stays where it is — never copied or moved).
  4. Adjust the image opacity, display scope, frosted glass (blur strength and glass color saturation, applied to the sidebar and composer card), per-region opacity (sidebar, conversation area, composer), and chat content offset as needed. Lower opacity values are more transparent and more immersive; the sidebar shows frosted glass in immersive fullscreen, while the composer takes effect in both modes.

Both entry points use the same plugin Config form, so changes made in one are reflected in the other. The top-level settings page is registered through settings.section; the row entry uses the modern plugins.row.config slot (the successor of the old settings.plugin.item settings card).

Configuration Storage

The settings live in the plugin's Config and are written by the DSH settings service into the profile patch (~/.dsh/profiles/<profile>/cordis.patch.yml) as an override of the row the bundle inserts:

- id: dsh-plugin-background-image
  config:
    enabled: true
    mode: fullscreen
    opacity: 0.9
    image: https://example.com/background.webp
    blur: 12             # frosted-glass blur (px, sidebar & composer card, 0 = off)
    conversationBlur: 0  # independent conversation blur (0–48 px)
    conversationOpacity: 0 # conversation opacity (0–1, both display modes)
    saturation: 1.4      # glass color saturation (1 = as-is, >1 = more vivid)
    sidebarOpacity: 0.5  # sidebar opacity (fullscreen only, via the pseudo-element glass)
    composerOpacity: 0.72 # composer opacity
    contentOffset: 120   # chat content horizontal offset (px, positive = right, negative = left)

Omitted fields use the schema defaults. settings.yaml is not used by this version; values saved by 1.2.x under the old background-image namespace are not read — set them once in the new config page after upgrading.

  • Everything is restored automatically after a page refresh or a DSH restart.
  • Local images are recorded as absolute paths — never copied or moved; the file stays where it is.

Browsers cannot load file:// resources directly due to security policies, so the plugin registers a read-only file-serving route on the host (GET /plugins/background-image/file?path=<absolute-path>) that serves the local image referenced by the configuration to the page over same-origin http. The route only accepts loopback origins and only serves the exact path currently referenced by the image field ("reference-as-authorization", the same model as the official session.attachment). If the image file is moved or deleted, the background stops working and the path must be set again.

Dependencies

Runtime dependencies

  • @deepseek-ai/schemastery: host-side Config schema definition and validation.
  • react (peer, optional): client-side settings UI.
  • Node.js built-ins: node:child_process, node:fs/promises, node:path.

Native file picker

  • Desktop app: no external command is needed — the renderer's hidden file input is converted to a real path by the preload bridge (window.__DSH_HOST_PATHS__.pathFor).
  • Web UI: the host opens the system dialog with the following commands:
PlatformRequired command
macOSosascript (bundled with the system)
Linuxzenity or kdialog (either one is enough)
Windowspowershell

When none of these is available, you can still type the local absolute path manually.

Known Limitations and Possible Impact

This plugin works by overriding DSH theme tokens and injecting CSS, which changes the global interface appearance. Keep the following in mind:

  1. Immersive fullscreen paints one fixed image layer: the plugin sets --dsw-alias-bg-base and --dsw-specific-sidebar-fill to transparent and draws the image once in body::before (position: fixed). This is what makes the same image appear continuously behind the sidebar, center column, detail column, and bottom row on both the Web UI and the Desktop window — including macOS Desktop, where the window itself is transparent and uses native vibrancy. Elements that paint --dsw-alias-bg-base directly (for example some tool panel surfaces) become see-through to the image; elements that use --dsw-alias-bg-layer-* / --dsw-alias-bg-overlay (menus, the Settings panel, floating dialogs) stay opaque.
  2. Conversation area only paints the image on the center column and keeps the native background elsewhere.
  3. Internal structure selectors use semantic suffixes and stable data attributes: the plugin targets [class*="_sidebarCol"], [class*="_centerCol"], [class*="_frame"], [data-rightbar-col], [data-shell-bottom], [data-phase][class*="_root"], [data-composer-seat], [class*="_viewArea"], [class*="_composerStack"], and [class*="_composerHero"] rather than a version's CSS-Module hash. A future DSH renaming of these semantic suffixes or attributes can still break the corresponding effect; the token-based image itself keeps working.
  4. Sidebar frosted glass relies on a pseudo-element approach: the glass is not applied to the sidebar ancestor itself but to <sidebar column>::before (an absolutely positioned overlay carrying the translucent fill and backdrop-filter), and the sidebar's content root is made position: relative so it paints above the glass. This keeps the sidebar from becoming the containing block for position: fixed popovers.
  5. Local image route: local images depend on the host-side read-only route (loopback only, reference-as-authorization). If the image file is moved or deleted, the background stops working until the path is set again. The plugin probes silently with HEAD requests on page load and whenever the settings page opens (no file content is transferred), and shows a hint at the top of the settings page and in the status line when invalid.
  6. Clean disable: the token overrides and internal-class styles above exist on the page only while the plugin is enabled (sidebar rules additionally require immersive fullscreen mode). Turning the plugin off removes the corresponding stylesheets entirely, fully restoring native DSH styles without leftover !important overrides.

Update and Uninstall

Update to the latest version:

npx @deepseek-ai/dsh plugin --profile <profile> add dsh-plugin-background-image@latest

Uninstall the plugin:

npx @deepseek-ai/dsh plugin --profile <profile> remove dsh-plugin-background-image

Requirements

  • Node.js 20 or later
  • DeepSeek Harness 0.2.1 or later (Web UI or Desktop). Version 1.2.x targeted the older settings.plugin.item / settings.register APIs and is not compatible with 0.2.1+.