From 29eeabad6956061aa974ab089b5020b0dd32236f Mon Sep 17 00:00:00 2001 From: Tsaop Date: Sun, 14 Apr 2024 20:07:56 +0200 Subject: [PATCH] Fix screen recording when pipewire is started after kwin (#1) This fixes screen recording when pipewire is started after kwin. In my specific case, I use an autostart script. Reviewed-on: https://git.crux.nu/ports/kde-plasma-6/pulls/1 Co-authored-by: Tsaop Co-committed-by: Tsaop --- kwin/.signature | 5 -- kwin/Pkgfile | 9 +- kwin/fix-screencast-pipewire.patch | 128 +++++++++++++++++++++++++++++ 3 files changed, 135 insertions(+), 7 deletions(-) delete mode 100644 kwin/.signature create mode 100644 kwin/fix-screencast-pipewire.patch diff --git a/kwin/.signature b/kwin/.signature deleted file mode 100644 index 03817ba..0000000 --- a/kwin/.signature +++ /dev/null @@ -1,5 +0,0 @@ -untrusted comment: verify with /etc/ports/kde-plasma-6.pub -RWTGxEYrvi0p3snzPSUTg02d675XCVVPO/v9sCXpPVYY87rVPpo+hdbLkN55Bkm4cocOIUNeWw+1v2EHwJAGmafTgAngZES3UQs= -SHA256 (Pkgfile) = 292c15cc9b759b4af2f9c1a1d3ec1cd6ed3e74fbbde4f58d09aac71883176e13 -SHA256 (.footprint) = 6e68ef8832d6e6657ed43d2db545437759acef90378a8c94856f4ac0d995d180 -SHA256 (kwin-6.0.3.1.tar.xz) = f15108a993206b962a3c5835b988a0b4922c0a9bc9ab80faf6b36a334d321b33 diff --git a/kwin/Pkgfile b/kwin/Pkgfile index 9201594..e860957 100644 --- a/kwin/Pkgfile +++ b/kwin/Pkgfile @@ -5,10 +5,15 @@ name=kwin version=6.0.3.1 -release=1 -source=(https://download.kde.org/stable/plasma/${version::5}/$name-$version.tar.xz) +release=2 +source=(https://download.kde.org/stable/plasma/${version::5}/$name-$version.tar.xz + fix-screencast-pipewire.patch) build() { + + # https://bugs.kde.org/show_bug.cgi?id=483137 + patch -Np1 -d $name-$version -i $SRC/fix-screencast-pipewire.patch + cmake -S $name-$version -B build -G Ninja \ -D CMAKE_INSTALL_PREFIX=/usr \ -D CMAKE_INSTALL_LIBDIR=lib \ diff --git a/kwin/fix-screencast-pipewire.patch b/kwin/fix-screencast-pipewire.patch new file mode 100644 index 0000000..a5dab53 --- /dev/null +++ b/kwin/fix-screencast-pipewire.patch @@ -0,0 +1,128 @@ +diff --git a/src/plugins/screencast/pipewirecore.cpp b/src/plugins/screencast/pipewirecore.cpp +index 077854c65e..eabf89a852 100644 +--- a/src/plugins/screencast/pipewirecore.cpp ++++ b/src/plugins/screencast/pipewirecore.cpp +@@ -94,6 +94,18 @@ bool PipeWireCore::init() + return true; + } + ++std::shared_ptr PipeWireCore::self() ++{ ++ static std::weak_ptr global; ++ auto ret = global.lock(); ++ if (!ret) { ++ ret = std::make_shared(); ++ ret->init(); ++ global = ret; ++ } ++ return ret; ++} ++ + } // namespace KWin + + #include "moc_pipewirecore.cpp" +diff --git a/src/plugins/screencast/screencastmanager.cpp b/src/plugins/screencast/screencastmanager.cpp +index 87c84e93f3..d0a2d6552d 100644 +--- a/src/plugins/screencast/screencastmanager.cpp ++++ b/src/plugins/screencast/screencastmanager.cpp +@@ -10,7 +10,6 @@ + #include "core/output.h" + #include "core/outputbackend.h" + #include "outputscreencastsource.h" +-#include "pipewirecore.h" + #include "regionscreencastsource.h" + #include "screencaststream.h" + #include "wayland/display.h" +@@ -27,9 +26,7 @@ namespace KWin + + ScreencastManager::ScreencastManager() + : m_screencast(new ScreencastV1Interface(waylandServer()->display(), this)) +- , m_core(new PipeWireCore) + { +- m_core->init(); + connect(m_screencast, &ScreencastV1Interface::windowScreencastRequested, this, &ScreencastManager::streamWindow); + connect(m_screencast, &ScreencastV1Interface::outputScreencastRequested, this, &ScreencastManager::streamWaylandOutput); + connect(m_screencast, &ScreencastV1Interface::virtualOutputScreencastRequested, this, &ScreencastManager::streamVirtualOutput); +@@ -46,7 +43,7 @@ void ScreencastManager::streamWindow(ScreencastStreamV1Interface *waylandStream, + return; + } + +- auto stream = new ScreenCastStream(new WindowScreenCastSource(window), m_core, this); ++ auto stream = new ScreenCastStream(new WindowScreenCastSource(window), this); + stream->setObjectName(window->desktopFileName()); + stream->setCursorMode(mode, 1, window->clientGeometry()); + +@@ -88,7 +85,7 @@ void ScreencastManager::streamOutput(ScreencastStreamV1Interface *waylandStream, + return; + } + +- auto stream = new ScreenCastStream(new OutputScreenCastSource(streamOutput), m_core, this); ++ auto stream = new ScreenCastStream(new OutputScreenCastSource(streamOutput), this); + stream->setObjectName(streamOutput->name()); + stream->setCursorMode(mode, streamOutput->scale(), streamOutput->geometry()); + +@@ -112,7 +109,7 @@ void ScreencastManager::streamRegion(ScreencastStreamV1Interface *waylandStream, + } + + auto source = new RegionScreenCastSource(geometry, scale); +- auto stream = new ScreenCastStream(source, m_core, this); ++ auto stream = new ScreenCastStream(source, this); + stream->setObjectName(rectToString(geometry)); + stream->setCursorMode(mode, scale, geometry); + +diff --git a/src/plugins/screencast/screencastmanager.h b/src/plugins/screencast/screencastmanager.h +index 059e64b545..c4829c0bd0 100644 +--- a/src/plugins/screencast/screencastmanager.h ++++ b/src/plugins/screencast/screencastmanager.h +@@ -16,7 +16,6 @@ namespace KWin + { + class Output; + class ScreenCastStream; +-class PipeWireCore; + + class ScreencastManager : public Plugin + { +@@ -47,7 +46,6 @@ private: + void integrateStreams(ScreencastStreamV1Interface *waylandStream, ScreenCastStream *stream); + + ScreencastV1Interface *m_screencast; +- std::shared_ptr m_core; + }; + + } // namespace KWin +diff --git a/src/plugins/screencast/screencaststream.cpp b/src/plugins/screencast/screencaststream.cpp +index 43d5044c17..183389704b 100644 +--- a/src/plugins/screencast/screencaststream.cpp ++++ b/src/plugins/screencast/screencaststream.cpp +@@ -321,9 +321,8 @@ void ScreenCastStream::onStreamRenegotiateFormat(uint64_t) + pw_stream_update_params(m_pwStream, params.data(), params.count()); + } + +-ScreenCastStream::ScreenCastStream(ScreenCastSource *source, std::shared_ptr pwCore, QObject *parent) ++ScreenCastStream::ScreenCastStream(ScreenCastSource *source, QObject *parent) + : QObject(parent) +- , m_pwCore(pwCore) + , m_source(source) + , m_resolution(source->textureSize()) + { +@@ -364,6 +363,7 @@ ScreenCastStream::~ScreenCastStream() + + bool ScreenCastStream::init() + { ++ m_pwCore = PipeWireCore::self(); + if (!m_pwCore->m_error.isEmpty()) { + m_error = m_pwCore->m_error; + return false; +diff --git a/src/plugins/screencast/screencaststream.h b/src/plugins/screencast/screencaststream.h +index 5abf2dd0bb..9afe32e080 100644 +--- a/src/plugins/screencast/screencaststream.h ++++ b/src/plugins/screencast/screencaststream.h +@@ -48,7 +48,7 @@ class KWIN_EXPORT ScreenCastStream : public QObject + { + Q_OBJECT + public: +- explicit ScreenCastStream(ScreenCastSource *source, std::shared_ptr pwCore, QObject *parent); ++ explicit ScreenCastStream(ScreenCastSource *source, QObject *parent); + ~ScreenCastStream(); + + bool init();