7d08e43c16
Honor the client's requested resolution by rendering a compositor virtual output at
exactly that size — native, headless, no scaling. There is no cross-compositor Wayland
protocol for this, so it's a per-compositor backend behind the (previously stubbed)
VirtualDisplay trait.
- vdisplay.rs: VirtualDisplay::create(mode) now returns a live VirtualOutput
{ node_id, remote_fd: Option<OwnedFd>, keepalive } with RAII teardown (drop releases
the output) instead of an inert OutputHandle + explicit destroy. Add compositor
detect() (LUMEN_COMPOSITOR / XDG_CURRENT_DESKTOP).
- vdisplay/kwin.rs: the KWin backend — the zkde_screencast_unstable_v1 stream_virtual_output
client (vendored protocol XML + wayland-scanner codegen). Creates a WxH output, returns
its PipeWire node (default daemon, remote_fd=None); a keepalive thread holds the Wayland
connection until dropped. (Moved here from capture/kwin.rs — it's a vdisplay backend, not
capture.)
- capture: generalize the PipeWire consumer to Option<OwnedFd> (portal remote vs. default
daemon) and add capture_virtual_output(vout), compositor-agnostic, owning the keepalive.
- gamestream/stream.rs: LUMEN_VIDEO_SOURCE=virtual creates a virtual display sized to the
client's cfg and captures it (self-contained, not pooled — a reconnect at a new
resolution gets a fresh output).
- m0: --source kwin-virtual goes through the trait.
Verified end-to-end against the running headless KWin: the request reaches the compositor
and is handled cleanly. Native creation needs a backend implementing createVirtualOutput —
the DRM backend, or the VirtualBackend since KWin 6.5.6; on this box's --virtual 6.4.5 it
returns "Could not find output" (expected; validates after the KWin upgrade). wlroots/Mutter
backends are the next ones to land on the same seam.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
106 lines
6.0 KiB
XML
106 lines
6.0 KiB
XML
<?xml version="1.0" encoding="UTF-8"?>
|
|
<protocol name="zkde_screencast_unstable_v1">
|
|
<copyright><![CDATA[
|
|
SPDX-FileCopyrightText: 2020-2021 Aleix Pol Gonzalez <aleixpol@kde.org>
|
|
|
|
SPDX-License-Identifier: LGPL-2.1-or-later
|
|
]]></copyright>
|
|
<interface name="zkde_screencast_unstable_v1" version="6">
|
|
<description summary="Protocol for managing PipeWire feeds of the different displays and windows">
|
|
Warning! The protocol described in this file is a desktop environment
|
|
implementation detail. Regular clients must not use this protocol.
|
|
Backward incompatible changes may be added without bumping the major
|
|
version of the extension.
|
|
</description>
|
|
|
|
<enum name="pointer">
|
|
<description summary="Stream consumer attachment attributes" />
|
|
<entry name="hidden" value="1" summary="No cursor"/>
|
|
<entry name="embedded" value="2" summary="Render the cursor on the stream"/>
|
|
<entry name="metadata" value="4" summary="Send metadata about where the cursor is through PipeWire"/>
|
|
</enum>
|
|
|
|
<request name="stream_output">
|
|
<description summary="requests a feed from a given source"/>
|
|
<arg name="stream" type="new_id" interface="zkde_screencast_stream_unstable_v1"/>
|
|
<arg name="output" type="object" interface="wl_output"/>
|
|
<arg name="pointer" type="uint" summary="Requested pointer mode"/>
|
|
</request>
|
|
<request name="stream_window">
|
|
<description summary="requests a feed from a given source"/>
|
|
<arg name="stream" type="new_id" interface="zkde_screencast_stream_unstable_v1"/>
|
|
<arg name="window_uuid" type="string" summary="window Identifier"/>
|
|
<arg name="pointer" type="uint" summary="Requested pointer mode"/>
|
|
</request>
|
|
|
|
<request name="destroy" type="destructor">
|
|
<description summary="Destroy the zkde_screencast_unstable_v1">
|
|
Destroy the zkde_screencast_unstable_v1 object.
|
|
</description>
|
|
</request>
|
|
|
|
<request name="stream_virtual_output" since="2">
|
|
<description summary="requests a feed from a new virtual output"/>
|
|
<arg name="stream" type="new_id" interface="zkde_screencast_stream_unstable_v1"/>
|
|
<arg name="name" type="string" summary="name of the created output"/>
|
|
<arg name="width" type="int" summary="Logical width resolution"/>
|
|
<arg name="height" type="int" summary="Logical height resolution"/>
|
|
<arg name="scale" type="fixed" summary="Scaling factor of the display where it's to be displayed"/>
|
|
<arg name="pointer" type="uint" summary="Requested pointer mode"/>
|
|
</request>
|
|
|
|
<request name="stream_region" since="3">
|
|
<description summary="requests a feed from region in the workspace">
|
|
Since version 5, the compositor will choose the highest scale
|
|
factor for the region if the given scale is 0.0.
|
|
</description>
|
|
<arg name="stream" type="new_id" interface="zkde_screencast_stream_unstable_v1"/>
|
|
|
|
<arg name="x" type="int" summary="Logical left position"/>
|
|
<arg name="y" type="int" summary="Logical top position"/>
|
|
<arg name="width" type="uint" summary="Logical width resolution"/>
|
|
<arg name="height" type="uint" summary="Logical height resolution"/>
|
|
<arg name="scale" type="fixed" summary="Scaling factor of the output recording"/>
|
|
<arg name="pointer" type="uint" summary="Requested pointer mode"/>
|
|
</request>
|
|
|
|
<request name="stream_virtual_output_with_description" since="4">
|
|
<description summary="requests a feed from a new virtual output"/>
|
|
<arg name="stream" type="new_id" interface="zkde_screencast_stream_unstable_v1"/>
|
|
<arg name="name" type="string" summary="name of the created output"/>
|
|
<arg name="description" type="string" summary="user visible description of the created output"/>
|
|
<arg name="width" type="int" summary="Logical width resolution"/>
|
|
<arg name="height" type="int" summary="Logical height resolution"/>
|
|
<arg name="scale" type="fixed" summary="Scaling factor of the display where it's to be displayed"/>
|
|
<arg name="pointer" type="uint" summary="Requested pointer mode"/>
|
|
</request>
|
|
</interface>
|
|
|
|
<interface name="zkde_screencast_stream_unstable_v1" version="6">
|
|
<request name="close" type="destructor">
|
|
<description summary="Indicates we are done with the stream and the communication is over."/>
|
|
</request>
|
|
<event name="closed">
|
|
<description summary="Notifies that the server has stopped the stream. Clients should now call close."/>
|
|
</event>
|
|
<event name="created" deprecated-since="6">
|
|
<description summary="Notifies about a pipewire feed being created">
|
|
Deprecated since version 6, use the object serial from the serial event instead
|
|
</description>
|
|
<arg name="node" type="uint" summary="node of the pipewire buffer"/>
|
|
</event>
|
|
<event name="failed">
|
|
<description summary="Offers an error message so the client knows the created event will not arrive, and the client should close the resource."/>
|
|
<arg name="error" type="string" summary="A human readable translated error message."/>
|
|
</event>
|
|
<event name="serial" since="6">
|
|
<description summary="the pipewire object serial">
|
|
The pipewire object serial of the stream. Should be preferred over the node id which is prone to id reuse.
|
|
Will be sent before the created event.
|
|
</description>
|
|
<arg name="object_serial_hi" type="uint" summary="high bits of the pipewire object serial"/>
|
|
<arg name="object_serial_low" type="uint" summary="low bits of the pipewire object serial"/>
|
|
</event>
|
|
</interface>
|
|
</protocol>
|