<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Recent changes to Create Web Architecture</title><link>https://sourceforge.net/p/sucrose/wiki/Create%2520Web%2520Architecture/</link><description>Recent changes to Create Web Architecture</description><atom:link href="https://sourceforge.net/p/sucrose/wiki/Create%20Web%20Architecture/feed" rel="self"/><language>en</language><lastBuildDate>Sat, 04 Jul 2026 04:15:50 -0000</lastBuildDate><atom:link href="https://sourceforge.net/p/sucrose/wiki/Create%20Web%20Architecture/feed" rel="self" type="application/rss+xml"/><item><title>Create Web Architecture modified by Bayram Emekli</title><link>https://sourceforge.net/p/sucrose/wiki/Create%2520Web%2520Architecture/</link><description>&lt;div class="markdown_content"&gt;&lt;pre&gt;--- v5
+++ v6
@@ -53,7 +53,7 @@

 2. Builds a single `Backgroundog` payload object (ten nullable JSON sub-objects) and serializes it to JSON.
 3. Sends it to the engine over the active transport — exactly one of **Pipe**, **Signal**, or **Transmission** (see below). The producer (Backgroundog) is the client; the engine is the server.

-Audio specifically comes from WASAPI loopback capture run through an FFT, producing the `Data` magnitude spectrum (`MaxSample = 128` samples) used by visualizers — see [Create Audio API](Create-Audio-API). Hardware and media-session info is polled by the same service — see [Backgroundog Service](Backgroundog-Service).
+Audio specifically comes from WASAPI loopback capture run through an FFT, producing the mono `Data` magnitude spectrum plus the per-channel `DataLeft` / `DataRight` — each `MaxSample = 128` samples normalised to `[0, 1]` (log-spaced 20 Hz–16 kHz) and used by visualizers — see [Create Audio API](Create-Audio-API). Hardware and media-session info is polled by the same service — see [Backgroundog Service](Backgroundog-Service).

 ## Step 4: ExecuteScriptAsync into the page

@@ -61,8 +61,8 @@

     :::js
     // You declared: "SystemAudio": "SucroseAudioData({0});"

-    // The engine runs: SucroseAudioData({ "Data":[...], "Title":"...", ... });
-    window.SucroseAudioData = function (obj) { spectrum = obj.Data; };
+    // The engine runs: SucroseAudioData({ "Data":[...], "DataLeft":[...], "DataRight":[...], "Title":"...", ... });
+    window.SucroseAudioData = function (obj) { spectrum = obj.Data; /* obj.DataLeft / obj.DataRight = per-channel */ };

 If a hook string is empty (or you never declared it), the engine does not fire it — so you only pay for the data categories you request.

&lt;/pre&gt;
&lt;/div&gt;</description><dc:creator xmlns:dc="http://purl.org/dc/elements/1.1/">Bayram Emekli</dc:creator><pubDate>Sat, 04 Jul 2026 04:15:50 -0000</pubDate><guid>https://sourceforge.net6fd647c6d37e2f32ed84c15ca49429c03d4a3f99</guid></item><item><title>Create Web Architecture modified by Bayram Emekli</title><link>https://sourceforge.net/p/sucrose/wiki/Create%2520Web%2520Architecture/</link><description>&lt;div class="markdown_content"&gt;&lt;pre&gt;--- v4
+++ v5
@@ -37,7 +37,7 @@

 2. The Live engine starts and, for a Web type, sets its source to your entry file (`Source` from the manifest, for example `Matrix.html`).
 3. Local web content is served by an internal **HTTP server** (`LocalHttpServer`) on `http://localhost:{port}/` and `http://127.0.0.1:{port}/`, where `{port}` is a free loopback port chosen automatically at startup. **Content is served over HTTP, not `file://`** — this matters because some browser security restrictions (modules, fetch, WebGL texture loads) behave differently under `file://`.

-GIF, Video, and YouTube types are loaded through generated HTML wrappers (`GifContent.html`, `VideoContent.html`, `YouTubeContent.html`); the `Url` type points the engine straight at the remote URL.
+Gif, Video, and YouTube types are loaded through generated HTML wrappers (`GifContent.html`, `VideoContent.html`, `YouTubeContent.html`); the `Url` type points the engine straight at the remote URL.

 ## Step 2: Properties applied on init

&lt;/pre&gt;
&lt;/div&gt;</description><dc:creator xmlns:dc="http://purl.org/dc/elements/1.1/">Bayram Emekli</dc:creator><pubDate>Sat, 04 Jul 2026 04:15:50 -0000</pubDate><guid>https://sourceforge.net65fc99dcbf800bed5fd2a0f903174deb1b21b204</guid></item><item><title>Create Web Architecture modified by Bayram Emekli</title><link>https://sourceforge.net/p/sucrose/wiki/Create%2520Web%2520Architecture/</link><description>&lt;div class="markdown_content"&gt;&lt;pre&gt;--- v3
+++ v4
@@ -27,7 +27,7 @@
 | **Sucrose.Commandog** | Launches the engine process (via its `Live` command) when you apply a wallpaper. The type → engine mapping itself is resolved upstream by the shared `Sucrose.Shared.Live.Helper.Run.Start()` launch logic (which reads `SucroseInfo.json`'s `Type` and looks up the configured engine) before the `Live` command is dispatched to Commandog. |
 | **Sucrose.Launcher / Sucrose.Portal** | UI and tray; trigger apply/restart and push customization changes. |

-&amp;gt; Only **WebView** and **CefSharp** participate in this data channel. The Backgroundog data pump is web-engine-only — MpvPlayer, Aurora, Nebula, Vexana, and Xavier do not receive the audio/system bundle. See [Choosing Engines](Choosing-Engines).
+&amp;gt; Only **WebView** and **CefSharp** participate in this data channel. The Backgroundog data pump is web-engine-only — MpvPlayer, VlcPlayer, Aurora, Nebula, Vexana, and Xavier do not receive the audio/system bundle. See [Choosing Engines](Choosing-Engines).

 ## Step 1: Engine launch and the local HTTP server

&lt;/pre&gt;
&lt;/div&gt;</description><dc:creator xmlns:dc="http://purl.org/dc/elements/1.1/">Bayram Emekli</dc:creator><pubDate>Sat, 04 Jul 2026 04:15:48 -0000</pubDate><guid>https://sourceforge.netf773c2eec3a321a5868c1e7a68cc6d09ba329e10</guid></item><item><title>Create Web Architecture modified by Bayram Emekli</title><link>https://sourceforge.net/p/sucrose/wiki/Create%2520Web%2520Architecture/</link><description>&lt;div class="markdown_content"&gt;&lt;pre&gt;--- v2
+++ v3
@@ -24,7 +24,7 @@
 |---------|-------------------------|
 | **Live engine** (`Sucrose.Live.WebView` or `Sucrose.Live.CefSharp`) | Hosts the browser, serves the page, runs JavaScript, receives the data bundle, and calls your callbacks. |
 | **Sucrose.Backgroundog** | Captures audio (WASAPI loopback → FFT) and polls hardware/media-session info, then ships a bundle to the engine. |
-| **Sucrose.Commandog** | Resolves the type → engine mapping and launches the engine when you apply a wallpaper. |
+| **Sucrose.Commandog** | Launches the engine process (via its `Live` command) when you apply a wallpaper. The type → engine mapping itself is resolved upstream by the shared `Sucrose.Shared.Live.Helper.Run.Start()` launch logic (which reads `SucroseInfo.json`'s `Type` and looks up the configured engine) before the `Live` command is dispatched to Commandog. |
 | **Sucrose.Launcher / Sucrose.Portal** | UI and tray; trigger apply/restart and push customization changes. |

 &amp;gt; Only **WebView** and **CefSharp** participate in this data channel. The Backgroundog data pump is web-engine-only — MpvPlayer, Aurora, Nebula, Vexana, and Xavier do not receive the audio/system bundle. See [Choosing Engines](Choosing-Engines).
&lt;/pre&gt;
&lt;/div&gt;</description><dc:creator xmlns:dc="http://purl.org/dc/elements/1.1/">Bayram Emekli</dc:creator><pubDate>Sat, 04 Jul 2026 04:15:46 -0000</pubDate><guid>https://sourceforge.netf67235fbeefdc8f56004db586b88a31ebcd5b40f</guid></item><item><title>Create Web Architecture modified by Bayram Emekli</title><link>https://sourceforge.net/p/sucrose/wiki/Create%2520Web%2520Architecture/</link><description>&lt;div class="markdown_content"&gt;&lt;pre&gt;--- v1
+++ v2
@@ -110,7 +110,22 @@
       (separately) properties applied on init and on change -&amp;gt; SucrosePropertyListener(name, val)
       (separately) raw mouse/keyboard -&amp;gt; Win32 messages -&amp;gt; page events

-&amp;gt; 🖼️ **Diagram needed:** Sequence diagram of the above — Backgroundog timer → build bundle → transport (Pipe/Signal/Transmission) → engine handler → `ExecuteScriptAsync` → page callbacks; with side branches for property push (init + change) and raw-input forwarding.

+    :::mermaid
+    sequenceDiagram
+        participant BG as Backgroundog
+        participant Eng as Browser engine
+        participant Page as Wallpaper page
+        Note over Eng: on apply: start local HTTP server, serve theme
+        Eng-&amp;gt;&amp;gt;Page: SucrosePropertyListener (init values)
+        loop each tick
+            BG-&amp;gt;&amp;gt;BG: collect 10 categories, build payload, to JSON
+            BG-&amp;gt;&amp;gt;Eng: send over Pipe / Signal / Transmission
+            Eng-&amp;gt;&amp;gt;Eng: deserialize, store as JSON strings
+            Eng-&amp;gt;&amp;gt;Page: for each hook, ExecuteScriptAsync
+            Note over Page: SucroseAudioData(obj), SucroseProcessorData(obj), ...
+        end
+        Note over Eng,Page: property change: FileSystemWatcher then SucrosePropertyListener
+        Note over Eng,Page: raw mouse/keyboard then Win32 messages then page events

 ## Why this matters to creators

&lt;/pre&gt;
&lt;/div&gt;</description><dc:creator xmlns:dc="http://purl.org/dc/elements/1.1/">Bayram Emekli</dc:creator><pubDate>Sat, 04 Jul 2026 04:15:43 -0000</pubDate><guid>https://sourceforge.net9b6210b86bad4cda2421eaa0b50efa1bcb1901c5</guid></item><item><title>Create Web Architecture modified by Bayram Emekli</title><link>https://sourceforge.net/p/sucrose/wiki/Create%2520Web%2520Architecture/</link><description>&lt;div class="markdown_content"&gt;&lt;h1 id="h-create-web-wallpaper-architecture"&gt;Create: Web Wallpaper Architecture&lt;/h1&gt;
&lt;p&gt;This page explains, end to end, &lt;strong&gt;how a Web wallpaper actually runs&lt;/strong&gt; inside Sucrose: how the page is served (a local HTTP server, not &lt;code&gt;file://&lt;/code&gt;), how live audio and system data flows from the &lt;strong&gt;Backgroundog&lt;/strong&gt; service across an inter-process channel into your page's JavaScript callbacks, how customization properties are pushed on start and on change, and how mouse and keyboard input reaches your page. It is the developer-facing companion to the creator pages — read it to understand the moving parts behind &lt;a href="./Create-Audio-API"&gt;Create Audio API&lt;/a&gt;, &lt;a href="./Create-System-API"&gt;Create System API&lt;/a&gt;, and &lt;a href="./Create-Property-Listener-Filters"&gt;Create Property Listener Filters&lt;/a&gt;.&lt;/p&gt;
&lt;h2 id="h-contents"&gt;Contents&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href="#the-processes-involved"&gt;The processes involved&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="#step-1-engine-launch-and-the-local-http-server"&gt;Step 1: Engine launch and the local HTTP server&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="#step-2-properties-applied-on-init"&gt;Step 2: Properties applied on init&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="#step-3-the-live-data-pump"&gt;Step 3: The live-data pump&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="#step-4-executescriptasync-into-the-page"&gt;Step 4: ExecuteScriptAsync into the page&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="#step-5-input-forwarding"&gt;Step 5: Input forwarding&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="#the-data-bundle"&gt;The data bundle&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="#transport-selection"&gt;Transport selection&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="#end-to-end-sequence"&gt;End-to-end sequence&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="#why-this-matters-to-creators"&gt;Why this matters to creators&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="#see-also"&gt;See also&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="h-the-processes-involved"&gt;The processes involved&lt;/h2&gt;
&lt;p&gt;A running Web wallpaper spans several separate Windows processes that coordinate over inter-process channels (Sucrose is multi-process by design — see &lt;a href="./Architecture-Overview"&gt;Architecture Overview&lt;/a&gt;):&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Process&lt;/th&gt;
&lt;th&gt;Role in a Web wallpaper&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Live engine&lt;/strong&gt; (&lt;code&gt;Sucrose.Live.WebView&lt;/code&gt; or &lt;code&gt;Sucrose.Live.CefSharp&lt;/code&gt;)&lt;/td&gt;
&lt;td&gt;Hosts the browser, serves the page, runs JavaScript, receives the data bundle, and calls your callbacks.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Sucrose.Backgroundog&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Captures audio (WASAPI loopback → FFT) and polls hardware/media-session info, then ships a bundle to the engine.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Sucrose.Commandog&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Resolves the type → engine mapping and launches the engine when you apply a wallpaper.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Sucrose.Launcher / Sucrose.Portal&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;UI and tray; trigger apply/restart and push customization changes.&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;blockquote&gt;
&lt;p&gt;Only &lt;strong&gt;WebView&lt;/strong&gt; and &lt;strong&gt;CefSharp&lt;/strong&gt; participate in this data channel. The Backgroundog data pump is web-engine-only — MpvPlayer, Aurora, Nebula, Vexana, and Xavier do not receive the audio/system bundle. See &lt;a href="./Choosing-Engines"&gt;Choosing Engines&lt;/a&gt;.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2 id="h-step-1-engine-launch-and-the-local-http-server"&gt;Step 1: Engine launch and the local HTTP server&lt;/h2&gt;
&lt;p&gt;When you apply a Web wallpaper:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Sucrose reads the theme's &lt;code&gt;SucroseInfo.json&lt;/code&gt;, sees &lt;code&gt;Type&lt;/code&gt; is &lt;code&gt;Web&lt;/code&gt; (value &lt;code&gt;2&lt;/code&gt;), and picks the configured engine for that type.&lt;/li&gt;
&lt;li&gt;The Live engine starts and, for a Web type, sets its source to your entry file (&lt;code&gt;Source&lt;/code&gt; from the manifest, for example &lt;code&gt;Matrix.html&lt;/code&gt;).&lt;/li&gt;
&lt;li&gt;Local web content is served by an internal &lt;strong&gt;HTTP server&lt;/strong&gt; (&lt;code&gt;LocalHttpServer&lt;/code&gt;) on &lt;code&gt;http://localhost:{port}/&lt;/code&gt; and &lt;code&gt;http://127.0.0.1:{port}/&lt;/code&gt;, where &lt;code&gt;{port}&lt;/code&gt; is a free loopback port chosen automatically at startup. &lt;strong&gt;Content is served over HTTP, not &lt;code&gt;file://&lt;/code&gt;&lt;/strong&gt; — this matters because some browser security restrictions (modules, fetch, WebGL texture loads) behave differently under &lt;code&gt;file://&lt;/code&gt;.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;GIF, Video, and YouTube types are loaded through generated HTML wrappers (&lt;code&gt;GifContent.html&lt;/code&gt;, &lt;code&gt;VideoContent.html&lt;/code&gt;, &lt;code&gt;YouTubeContent.html&lt;/code&gt;); the &lt;code&gt;Url&lt;/code&gt; type points the engine straight at the remote URL.&lt;/p&gt;
&lt;h2 id="h-step-2-properties-applied-on-init"&gt;Step 2: Properties applied on init&lt;/h2&gt;
&lt;p&gt;On initialization, the engine reads your &lt;code&gt;SucroseProperties.json&lt;/code&gt; (or an encoded variant) and applies &lt;strong&gt;all current property values&lt;/strong&gt; by calling your &lt;code&gt;SucrosePropertyListener&lt;/code&gt; once per property. This means your wallpaper always starts in the user's last-saved configuration — you do not need to read settings yourself. See &lt;a href="./Create-Property-Listener-Filters"&gt;Create Property Listener Filters&lt;/a&gt; and &lt;a href="./Create-Customization-Controls"&gt;Create Customization Controls&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;When the user later changes a control in the Portal, the engine's &lt;code&gt;FileSystemWatcher&lt;/code&gt; detects the updated properties file and re-pushes the changed values to the running page via the same call — live, no restart. The trigger file is cleaned up after ~3 seconds.&lt;/p&gt;
&lt;h2 id="h-step-3-the-live-data-pump"&gt;Step 3: The live-data pump&lt;/h2&gt;
&lt;p&gt;Independently of properties, the &lt;strong&gt;Backgroundog&lt;/strong&gt; service runs a periodic timer. On each tick it:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Calls a &lt;code&gt;Get*Info()&lt;/code&gt; collector for each category: &lt;code&gt;Bios&lt;/code&gt;, &lt;code&gt;Date&lt;/code&gt;, &lt;code&gt;Audio&lt;/code&gt;, &lt;code&gt;Memory&lt;/code&gt;, &lt;code&gt;Battery&lt;/code&gt;, &lt;code&gt;Graphic&lt;/code&gt;, &lt;code&gt;Network&lt;/code&gt;, &lt;code&gt;Storage&lt;/code&gt;, &lt;code&gt;Processor&lt;/code&gt;, &lt;code&gt;Motherboard&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;Builds a single &lt;code&gt;Backgroundog&lt;/code&gt; payload object (ten nullable JSON sub-objects) and serializes it to JSON.&lt;/li&gt;
&lt;li&gt;Sends it to the engine over the active transport — exactly one of &lt;strong&gt;Pipe&lt;/strong&gt;, &lt;strong&gt;Signal&lt;/strong&gt;, or &lt;strong&gt;Transmission&lt;/strong&gt; (see below). The producer (Backgroundog) is the client; the engine is the server.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;Audio specifically comes from WASAPI loopback capture run through an FFT, producing the &lt;code&gt;Data&lt;/code&gt; magnitude spectrum (&lt;code&gt;MaxSample = 128&lt;/code&gt; samples) used by visualizers — see &lt;a href="./Create-Audio-API"&gt;Create Audio API&lt;/a&gt;. Hardware and media-session info is polled by the same service — see &lt;a href="./Backgroundog-Service"&gt;Backgroundog Service&lt;/a&gt;.&lt;/p&gt;
&lt;h2 id="h-step-4-executescriptasync-into-the-page"&gt;Step 4: ExecuteScriptAsync into the page&lt;/h2&gt;
&lt;p&gt;On the engine side, the transport's handler receives the JSON, deserializes it back into the &lt;code&gt;Backgroundog&lt;/code&gt; payload, and stores each non-null sub-object as a JSON string in the engine's internal fields (&lt;code&gt;AudioData&lt;/code&gt;, &lt;code&gt;ProcessorData&lt;/code&gt;, &lt;code&gt;MemoryData&lt;/code&gt;, …). Then, for each &lt;strong&gt;non-empty&lt;/strong&gt; hook you declared in &lt;code&gt;SucroseCompatible.json&lt;/code&gt;, the engine formats your template with the stored JSON (&lt;code&gt;string.Format(hook, json)&lt;/code&gt;) and runs it via &lt;code&gt;ExecuteScriptAsync&lt;/code&gt; on the WebView2/CefSharp page. That call invokes your JavaScript function:&lt;/p&gt;
&lt;div class="codehilite"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="c1"&gt;// You declared: "SystemAudio": "SucroseAudioData({0});"&lt;/span&gt;
&lt;span class="c1"&gt;// The engine runs: SucroseAudioData({ "Data":[...], "Title":"...", ... });&lt;/span&gt;
&lt;span class="nb"&gt;window&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;SucroseAudioData&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;obj&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;spectrum&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;obj&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;Data&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;If a hook string is empty (or you never declared it), the engine does not fire it — so you only pay for the data categories you request.&lt;/p&gt;
&lt;h2 id="h-step-5-input-forwarding"&gt;Step 5: Input forwarding&lt;/h2&gt;
&lt;p&gt;When the desktop is focused, mouse and keyboard activity is forwarded into the page. The browser engines reference Sucrose's raw-input layer, translating raw input into Win32 messages (and a synthetic scroll script) so that standard web events — &lt;code&gt;mousemove&lt;/code&gt;, &lt;code&gt;click&lt;/code&gt;, &lt;code&gt;wheel&lt;/code&gt;, &lt;code&gt;keydown&lt;/code&gt; — fire inside your wallpaper. This is what makes Web wallpapers interactive (for example, the Fluid Simulation Showcase reacts to the cursor). See &lt;a href="./Type-Web"&gt;Type-Web&lt;/a&gt;.&lt;/p&gt;
&lt;h2 id="h-the-data-bundle"&gt;The data bundle&lt;/h2&gt;
&lt;p&gt;The bundle that crosses the channel is the same regardless of transport — ten nullable JSON sub-objects:&lt;/p&gt;
&lt;div class="codehilite"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;Bios, Date, Audio, Memory, Battery, Graphic, Network, Storage, Processor, Motherboard
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;Each non-null sub-object is re-serialized on the engine side and fanned out to its matching &lt;code&gt;SucroseCompatible.json&lt;/code&gt; hook. The &lt;code&gt;Audio&lt;/code&gt; sub-object is the audio-reactive channel; the other nine are the System Status API. Field-by-field documentation lives on &lt;a href="./Create-Audio-API"&gt;Create Audio API&lt;/a&gt; and &lt;a href="./Create-System-API"&gt;Create System API&lt;/a&gt;.&lt;/p&gt;
&lt;h2 id="h-transport-selection"&gt;Transport selection&lt;/h2&gt;
&lt;p&gt;The live-data channel can use one of three interchangeable transports, chosen by the &lt;code&gt;CommunicationType&lt;/code&gt; setting (default &lt;strong&gt;Transmission&lt;/strong&gt;). They carry the identical JSON payload — only the carrier differs.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Transport&lt;/th&gt;
&lt;th&gt;Mechanism&lt;/th&gt;
&lt;th&gt;Channel name&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Transmission&lt;/strong&gt; &lt;em&gt;(default)&lt;/em&gt;&lt;/td&gt;
&lt;td&gt;TCP on the loopback address (&lt;code&gt;127.0.0.1&lt;/code&gt;) at a dynamically allocated port (saved to &lt;code&gt;TransmissionPort&lt;/code&gt;)&lt;/td&gt;
&lt;td&gt;created on demand&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Pipe&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Named pipe (&lt;code&gt;System.IO.Pipes&lt;/code&gt;)&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Sucrose.Wallpaper.Engine.Backgroundog.Pipe&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Signal&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;JSON file + &lt;code&gt;FileSystemWatcher&lt;/code&gt; under &lt;code&gt;%AppData%\Sucrose\Cache\SignalT&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Backgroundog.sgnl&lt;/code&gt; (with GUID-suffixed instances)&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;The engine picks the transport from &lt;code&gt;CommunicationType&lt;/code&gt; and stands up exactly one server; Backgroundog reads the same setting (and the engine-set &lt;code&gt;*Required&lt;/code&gt;/&lt;code&gt;TransmissionPort&lt;/code&gt; flags) to know which client to use. Full details, including the &lt;code&gt;Launcher&lt;/code&gt; tray-control channel, are on the &lt;a href="./IPC"&gt;IPC&lt;/a&gt; page.&lt;/p&gt;
&lt;h2 id="h-end-to-end-sequence"&gt;End-to-end sequence&lt;/h2&gt;
&lt;div class="codehilite"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;[Sucrose.Backgroundog]                          [Sucrose.Live.WebView | CefSharp]&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="na"&gt;periodic timer&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="na"&gt;collect Bios/Date/Audio/Memory/Battery/&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="na"&gt;Graphic/Network/Storage/&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="na"&gt;Processor/Motherboard (JObject)&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="na"&gt;build Backgroundog payload -&amp;gt; JSON&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="na"&gt;send over CommunicationType transport  ----&amp;gt; server receives JSON&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="na"&gt;(Pipe | Signal | Transmission)               deserialize -&amp;gt; Backgroundog payload&lt;/span&gt;
&lt;span class="w"&gt;                                                      &lt;/span&gt;&lt;span class="na"&gt;store each non-null field as JSON string&lt;/span&gt;
&lt;span class="w"&gt;                                                      &lt;/span&gt;&lt;span class="na"&gt;for each non-empty SucroseCompatible hook&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
&lt;span class="w"&gt;                                                        &lt;/span&gt;&lt;span class="na"&gt;string.Format(hook, json)&lt;/span&gt;
&lt;span class="w"&gt;                                                        &lt;/span&gt;&lt;span class="na"&gt;ExecuteScriptAsync(js)  ----&amp;gt; page JS&lt;/span&gt;
&lt;span class="w"&gt;                                                                                       &lt;/span&gt;&lt;span class="na"&gt;SucroseAudioData(obj)&lt;/span&gt;
&lt;span class="w"&gt;                                                                                       &lt;/span&gt;&lt;span class="na"&gt;SucroseProcessorData(obj)&lt;/span&gt;
&lt;span class="w"&gt;                                                                                       &lt;/span&gt;&lt;span class="na"&gt;...&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="na"&gt;(separately) properties applied on init and on change -&amp;gt; SucrosePropertyListener(name, val)&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="na"&gt;(separately) raw mouse/keyboard -&amp;gt; Win32 messages -&amp;gt; page events&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;blockquote&gt;
&lt;p&gt;🖼️ &lt;strong&gt;Diagram needed:&lt;/strong&gt; Sequence diagram of the above — Backgroundog timer → build bundle → transport (Pipe/Signal/Transmission) → engine handler → &lt;code&gt;ExecuteScriptAsync&lt;/code&gt; → page callbacks; with side branches for property push (init + change) and raw-input forwarding.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2 id="h-why-this-matters-to-creators"&gt;Why this matters to creators&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;You receive data; you do not poll for it.&lt;/strong&gt; Implement the &lt;code&gt;Sucrose*Data&lt;/code&gt; callbacks and Sucrose calls them on each tick — there is no API to request a reading on demand.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Serve-over-HTTP changes behavior vs &lt;code&gt;file://&lt;/code&gt;.&lt;/strong&gt; Relative paths, modules, fetch, and WebGL all run against &lt;code&gt;http://localhost:{port}/&lt;/code&gt;, so author your page as if it were on a tiny web server.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Declare only the hooks you use.&lt;/strong&gt; Each enabled hook adds collection and &lt;code&gt;ExecuteScriptAsync&lt;/code&gt; work; unused categories are never pushed.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Properties arrive on start and on every change.&lt;/strong&gt; Keep &lt;code&gt;SucrosePropertyListener&lt;/code&gt; cheap and idempotent — it is called repeatedly, including for live re-application.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Interactivity is automatic&lt;/strong&gt; on the browser engines when the desktop is focused; build with normal DOM event listeners.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Web-engine only.&lt;/strong&gt; The whole data pump, JS bridge, and input forwarding apply to WebView/CefSharp. If your callbacks never fire, confirm the wallpaper is running on a browser engine. See &lt;a href="./Choosing-Engines"&gt;Choosing Engines&lt;/a&gt;.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="h-see-also"&gt;See also&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href="./Create-Audio-API"&gt;Create Audio API&lt;/a&gt; — the &lt;code&gt;SucroseAudioData&lt;/code&gt; payload (FFT + now-playing)&lt;/li&gt;
&lt;li&gt;&lt;a href="./Create-System-API"&gt;Create System API&lt;/a&gt; — the nine system-status callbacks&lt;/li&gt;
&lt;li&gt;&lt;a href="./Create-Property-Listener-Filters"&gt;Create Property Listener Filters&lt;/a&gt; — how property changes reach your page&lt;/li&gt;
&lt;li&gt;&lt;a href="./IPC"&gt;IPC&lt;/a&gt; — Pipe/Signal/Transmission transports in depth&lt;/li&gt;
&lt;li&gt;&lt;a href="./Backgroundog-Service"&gt;Backgroundog Service&lt;/a&gt; — the data producer&lt;/li&gt;
&lt;li&gt;&lt;a href="./Type-Web"&gt;Type-Web&lt;/a&gt; — the Web wallpaper type&lt;/li&gt;
&lt;li&gt;&lt;a href="./Engine-WebView"&gt;Engine-WebView&lt;/a&gt; and &lt;a href="./Engine-CefSharp"&gt;Engine-CefSharp&lt;/a&gt; — the browser engines&lt;/li&gt;
&lt;/ul&gt;&lt;/div&gt;</description><dc:creator xmlns:dc="http://purl.org/dc/elements/1.1/">Bayram Emekli</dc:creator><pubDate>Sat, 04 Jul 2026 04:15:24 -0000</pubDate><guid>https://sourceforge.netdfea3d28d30d071e551fa472c7648484675529f4</guid></item></channel></rss>