Draw all of a client's views in one renderer process
CI / build (push) Successful in 40s

The adapter starts one renderer process per client, with the first engine
(again if it has exited), and attaches each engine's channel to it through a
control section (protocol version 5: Control, the -attach event). The renderer
process keeps a window, swap chain and scene per channel on one Direct3D
device, takes the views' frames in turns, and closes a view when its engine
does.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
This commit is contained in:
dhkatzandClaude Opus 5.5 committed 2026-10-28 19:16:01 -07:00
1 parent 6e4fe589e5
commit 8055099920
5 files changed
+404 -195

No files matched your search

+12 -8
View File
@@ -19,13 +19,17 @@ Direct3D 11 backend is built for now.
## How they talk
`include/t5de/protocol/` is shared by both builds, so it uses fixed-size fields only. For each engine the client
creates (each 3D view, and again on room changes), the adapter:
`include/t5de/protocol/` is shared by both builds, so it uses fixed-size fields only. One renderer process draws all
of a client's 3D views, with one Direct3D device. The adapter starts `t5de-renderer.exe --control <name> --parent
<pid>` from its own folder with the first engine (again with the next one if it has exited), and creates a control
section (`Local\t5de-renderer-<pid>`, `protocol::Control`). For each engine the client creates (each 3D view: Home's
avatar, the room, ...), the adapter:
1. creates a shared memory channel (`Local\t5de-renderer-<pid>-<n>`) holding IMVU's window handle and a frame
count, and an event set after each frame;
2. starts `t5de-renderer.exe --channel <name> --parent <pid>` from its own folder;
3. sets the event at each `endRendering`, and sets `closing` when the engine is destroyed.
1. creates a shared memory channel (`<control name>-<n>`) holding IMVU's window handle, and its events;
2. counts it in the control section and sets `<control name>-attach`, and the renderer process opens it, with a
child window, swap chain and scene of its own;
3. sends each frame's commands through it, and sets `closing` when the engine is destroyed (the renderer process
then closes the view).
The renderer process draws into a child window it creates inside the client's window: window handles are valid in
every process, and Windows allows child windows across processes (Chrome's GPU process works this way). The child
@@ -34,7 +38,7 @@ compositor shows above the client's own drawing. The client's window must not cl
which the client creates it with, so the adapter clears it):
the client draws a frame when its window gets `WM_PAINT` (`SceneWindow.dll` invalidates it, and draws on the paint),
and a window entirely covered by clipped children never gets one, so the client fell to about one frame a second.
The process exits when the engine is destroyed or the client exits.
The process exits when the client exits.
## Status
@@ -76,7 +80,7 @@ pipelines draw both), and a pixmap target's frame is read back through the chann
`-read` event) into its Pixmap, as the client's renderer does, synchronously. A read back must fit in the channel's
data area (16 MB: the client's 2048x2048 snapshots just do). Checked with outfit pictures and photos.
Next: one renderer process for all of a client's views.
Next: sharing pipelines between views (each view's scene compiles its own), and higher frame rates.
## Building