Use native portal capture for Wayland broadcasts
This commit is contained in:
1 parent
ce0fa1f063
commit
44c9c3bcaf
3 files changed
+35
-1
No files matched your search
@@ -34,6 +34,9 @@ extern "C" {
|
||||
#ifdef UTUN_STREAM_X11_CURSOR
|
||||
#include "stream_screen_cursor.h"
|
||||
#endif
|
||||
#ifdef UTUN_STREAM_PORTAL
|
||||
#include "stream_portal_capture.h"
|
||||
#endif
|
||||
|
||||
namespace {
|
||||
int64_t monotonicUs() { return std::chrono::duration_cast<std::chrono::microseconds>(
|
||||
@@ -77,6 +80,9 @@ struct StreamPublishEngine::Impl {
|
||||
std::unique_ptr<QVideoSink> sink;
|
||||
std::unique_ptr<QCamera> camera;
|
||||
std::unique_ptr<QScreenCapture> screen;
|
||||
#ifdef UTUN_STREAM_PORTAL
|
||||
std::unique_ptr<StreamPortalCapture> portal;
|
||||
#endif
|
||||
std::unique_ptr<QTimer> screenGrabTimer;
|
||||
#ifdef UTUN_STREAM_X11_CURSOR
|
||||
std::unique_ptr<StreamScreenCursor> cursor;
|
||||
@@ -148,6 +154,9 @@ QVariant StreamPublishEngine::previewFrame() const {
|
||||
}
|
||||
QList<int> StreamPublishEngine::codecs() const { std::lock_guard<std::mutex> guard(m->lock); return m->codecs; }
|
||||
bool StreamPublishEngine::cursorSupported(const StreamVideoSource& source) {
|
||||
#ifdef UTUN_STREAM_PORTAL
|
||||
if (source.kind == StreamVideoSource::Screen && source.id == "portal") return true;
|
||||
#endif
|
||||
#ifdef UTUN_STREAM_X11_CURSOR
|
||||
return source.kind == StreamVideoSource::Screen && source.screen && source.id != "portal" && QGuiApplication::platformName() == "xcb";
|
||||
#else
|
||||
@@ -267,6 +276,14 @@ bool StreamPublishEngine::openSource(const StreamPublishConfig& config) {
|
||||
if (screen == config.source.screen && screenId(screen) == config.source.id) { selected = screen; break; }
|
||||
if (!selected) { DEBUG_ERROR(DEBUG_CATEGORY_VIDEO, "desktop screen disappeared"); return false; }
|
||||
}
|
||||
#ifdef UTUN_STREAM_PORTAL
|
||||
if (config.source.id == "portal") {
|
||||
m->portal = std::make_unique<StreamPortalCapture>();
|
||||
connect(m->portal.get(), &StreamPortalCapture::frameReady, m->sink.get(), &QVideoSink::setVideoFrame);
|
||||
connect(m->portal.get(), &StreamPortalCapture::errorOccurred, this, failed, Qt::QueuedConnection);
|
||||
m->portal->start(config.showCursor);
|
||||
} else
|
||||
#endif
|
||||
// Qt X11 screen capture ищет root по имени и путает мониторы; QScreen захватывает именно выбранный экран.
|
||||
if (selected && QGuiApplication::platformName() == "xcb") {
|
||||
#ifdef UTUN_STREAM_X11_CURSOR
|
||||
@@ -340,6 +357,9 @@ bool StreamPublishEngine::openSource(const StreamPublishConfig& config) {
|
||||
void StreamPublishEngine::closeSource() {
|
||||
#ifdef HAVE_STREAM_CAPTURE
|
||||
m->screenGrabTimer.reset();
|
||||
#ifdef UTUN_STREAM_PORTAL
|
||||
m->portal.reset();
|
||||
#endif
|
||||
#ifdef UTUN_STREAM_X11_CURSOR
|
||||
m->cursor.reset();
|
||||
#endif
|
||||
@@ -388,6 +408,10 @@ bool StreamPublishEngine::start(uint64_t group, const StreamPublishConfig& confi
|
||||
bool StreamPublishEngine::reconfigure(const StreamPublishConfig& config) {
|
||||
if (!m->running) return false;
|
||||
StreamPublishConfig previous = this->config();
|
||||
if (previous.source.id == "portal" && config.source.sameSource(previous.source) && config.showCursor != previous.showCursor) {
|
||||
DEBUG_WARN(DEBUG_CATEGORY_VIDEO, "Wayland capture cursor mode cannot change during a portal session");
|
||||
emit errorOccurred(text("Change cursor visibility before starting screen sharing")); return false;
|
||||
}
|
||||
if (config.audio != previous.audio || config.microphone != previous.microphone) {
|
||||
DEBUG_WARN(DEBUG_CATEGORY_STREAM, "desktop microphone selection changed during live publication");
|
||||
emit errorOccurred(text("Change the microphone before starting the stream")); return false;
|
||||
|
||||
Reference in new issue
Block a user