diff --git a/src/librssguard/gui/mediaplayer/libmpv/libmpvbackend.cpp b/src/librssguard/gui/mediaplayer/libmpv/libmpvbackend.cpp index d8ce103bb..37a9489d5 100644 --- a/src/librssguard/gui/mediaplayer/libmpv/libmpvbackend.cpp +++ b/src/librssguard/gui/mediaplayer/libmpv/libmpvbackend.cpp @@ -84,7 +84,7 @@ LibMpvBackend::~LibMpvBackend() { } } -void LibMpvBackend::handle_mpv_event(mpv_event* event) { +void LibMpvBackend::handleMpvEvent(mpv_event* event) { switch (event->event_id) { case MPV_EVENT_PROPERTY_CHANGE: { mpv_event_property* prop = (mpv_event_property*)event->data; @@ -103,8 +103,8 @@ void LibMpvBackend::handle_mpv_event(mpv_event* event) { QVariant v = mpv::qt::node_to_variant((mpv_node*)prop->data); // Abuse JSON support for easily printing the mpv_node contents. QJsonDocument d = QJsonDocument::fromVariant(v); - append_log("Change property " + QString(prop->name) + ":\n"); - append_log(d.toJson().data()); + appendLog("Change property " + QString(prop->name) + ":\n"); + appendLog(d.toJson().data()); } } break; @@ -155,11 +155,11 @@ void LibMpvBackend::onMpvEvents() { break; } - handle_mpv_event(event); + handleMpvEvent(event); } } -void LibMpvBackend::append_log(const QString& text) { +void LibMpvBackend::appendLog(const QString& text) { qDebugNN << LOGSEC_MPV << text; } diff --git a/src/librssguard/gui/mediaplayer/libmpv/libmpvbackend.h b/src/librssguard/gui/mediaplayer/libmpv/libmpvbackend.h index d39a00cfb..06af15cf2 100644 --- a/src/librssguard/gui/mediaplayer/libmpv/libmpvbackend.h +++ b/src/librssguard/gui/mediaplayer/libmpv/libmpvbackend.h @@ -38,9 +38,9 @@ class LibMpvBackend : public PlayerBackend { void launchMpvEvents(); private: - void append_log(const QString& text); - void create_player(); - void handle_mpv_event(mpv_event* event); + void appendLog(const QString& text); + void createPlayer(); + void handleMpvEvent(mpv_event* event); private: QWidget* m_mpvContainer; diff --git a/src/librssguard/gui/mediaplayer/libmpv/libmpvwidget.cpp b/src/librssguard/gui/mediaplayer/libmpv/libmpvwidget.cpp deleted file mode 100644 index b160b28c4..000000000 --- a/src/librssguard/gui/mediaplayer/libmpv/libmpvwidget.cpp +++ /dev/null @@ -1,174 +0,0 @@ -// For license of this file, see /LICENSE.md. - -#include "gui/mediaplayer/libmpv/libmpvwidget.h" - -#include "gui/mediaplayer/libmpv/qthelper.h" - -#include -#include - -#include - -#include -#include - -static void wakeup(void* ctx) { - QMetaObject::invokeMethod((LibMpvWidget*)ctx, "on_mpv_events", Qt::QueuedConnection); -} - -static void* get_proc_address(void* ctx, const char* name) { - Q_UNUSED(ctx); - QOpenGLContext* glctx = QOpenGLContext::currentContext(); - if (!glctx) - return nullptr; - return reinterpret_cast(glctx->getProcAddress(QByteArray(name))); -} - -LibMpvWidget::LibMpvWidget(QWidget* parent, Qt::WindowFlags f) : QOpenGLWidget(parent, f) { - mpv = mpv_create(); - if (!mpv) - throw std::runtime_error("could not create mpv context"); - - mpv_set_option_string(mpv, "terminal", "yes"); - mpv_set_option_string(mpv, "msg-level", "all=v"); - - mpv_set_option_string(mpv, "input-default-bindings", "yes"); - /* - mpv_set_option_string( - mpv, "config-dir", - "c:\\Users\\rotter\\Downloads\\mpv-examples-master\\mpv-examples-" - "master\\libmpv\\build-qt_opengl-Desktop_Qt_6_6_0_MSVC2017_64bit-" - "Debug\\debug\\"); -*/ - /* - mpv_set_option_string(mpv, "input-conf", "input.conf"); - */ - - if (mpv_initialize(mpv) < 0) - throw std::runtime_error("could not initialize mpv context"); - - // Request hw decoding, just for testing. - mpv::qt::set_option_variant(mpv, "hwdec", "auto"); - - mpv_observe_property(mpv, 0, "duration", MPV_FORMAT_DOUBLE); - mpv_observe_property(mpv, 0, "time-pos", MPV_FORMAT_DOUBLE); - mpv_set_wakeup_callback(mpv, wakeup, this); - - installEventFilter(this); -} - -LibMpvWidget::~LibMpvWidget() { - makeCurrent(); - if (mpv_gl) - mpv_render_context_free(mpv_gl); - mpv_terminate_destroy(mpv); -} - -void LibMpvWidget::command(const QVariant& params) { - mpv::qt::command_variant(mpv, params); -} - -void LibMpvWidget::setProperty(const QString& name, const QVariant& value) { - mpv::qt::set_property_variant(mpv, name, value); -} - -QVariant LibMpvWidget::getProperty(const QString& name) const { - return mpv::qt::get_property_variant(mpv, name); -} - -void LibMpvWidget::initializeGL() { - mpv_opengl_init_params gl_init_params[1] = {get_proc_address, nullptr}; - mpv_render_param params[]{{MPV_RENDER_PARAM_API_TYPE, const_cast(MPV_RENDER_API_TYPE_OPENGL)}, - {MPV_RENDER_PARAM_OPENGL_INIT_PARAMS, &gl_init_params}, - {MPV_RENDER_PARAM_INVALID, nullptr}}; - - if (mpv_render_context_create(&mpv_gl, mpv, params) < 0) - throw std::runtime_error("failed to initialize mpv GL context"); - mpv_render_context_set_update_callback(mpv_gl, LibMpvWidget::on_update, reinterpret_cast(this)); -} - -void LibMpvWidget::paintGL() { - mpv_opengl_fbo mpfbo{static_cast(defaultFramebufferObject()), width(), height(), 0}; - int flip_y{1}; - - mpv_render_param params[] = {{MPV_RENDER_PARAM_OPENGL_FBO, &mpfbo}, - {MPV_RENDER_PARAM_FLIP_Y, &flip_y}, - {MPV_RENDER_PARAM_INVALID, nullptr}}; - // See render_gl.h on what OpenGL environment mpv expects, and - // other API details. - mpv_render_context_render(mpv_gl, params); -} - -void LibMpvWidget::on_mpv_events() { - // Process all events, until the event queue is empty. - while (mpv) { - mpv_event* event = mpv_wait_event(mpv, 0); - if (event->event_id == MPV_EVENT_NONE) { - break; - } - handle_mpv_event(event); - } -} - -void LibMpvWidget::handle_mpv_event(mpv_event* event) { - switch (event->event_id) { - case MPV_EVENT_PROPERTY_CHANGE: { - mpv_event_property* prop = (mpv_event_property*)event->data; - if (strcmp(prop->name, "time-pos") == 0) { - if (prop->format == MPV_FORMAT_DOUBLE) { - double time = *(double*)prop->data; - Q_EMIT positionChanged(time); - } - } - else if (strcmp(prop->name, "duration") == 0) { - if (prop->format == MPV_FORMAT_DOUBLE) { - double time = *(double*)prop->data; - Q_EMIT durationChanged(time); - } - } - break; - } - default:; - // Ignore uninteresting or unknown events. - } -} - -// Make Qt invoke mpv_render_context_render() to draw a new/updated video frame. -void LibMpvWidget::maybeUpdate() { - // If the Qt window is not visible, Qt's update() will just skip rendering. - // This confuses mpv's render API, and may lead to small occasional - // freezes due to video rendering timing out. - // Handle this by manually redrawing. - // Note: Qt doesn't seem to provide a way to query whether update() will - // be skipped, and the following code still fails when e.g. switching - // to a different workspace with a reparenting window manager. - if (window()->isMinimized()) { - makeCurrent(); - paintGL(); - context()->swapBuffers(context()->surface()); - doneCurrent(); - } - else { - update(); - } -} - -void LibMpvWidget::on_update(void* ctx) { - QMetaObject::invokeMethod((LibMpvWidget*)ctx, "maybeUpdate"); -} - -void LibMpvWidget::keyPressEvent(QKeyEvent* event) { - mpv_set_option_string(mpv, "keypress", event->text().toLocal8Bit().constData()); -} - -bool LibMpvWidget::eventFilter(QObject* watched, QEvent* event) { - if (event->type() == QEvent::Type::KeyPress) { - QString txt = dynamic_cast(event)->text(); - - command(QStringList() << "keypress" << txt.toLocal8Bit().constData()); - - return true; - } - - return false; -} diff --git a/src/librssguard/gui/mediaplayer/libmpv/libmpvwidget.h b/src/librssguard/gui/mediaplayer/libmpv/libmpvwidget.h deleted file mode 100644 index 35fbd890f..000000000 --- a/src/librssguard/gui/mediaplayer/libmpv/libmpvwidget.h +++ /dev/null @@ -1,55 +0,0 @@ -// For license of this file, see /LICENSE.md. - -#ifndef LIBMPVWIDGET_H -#define LIBMPVWIDGET_H - -#include - -struct mpv_handle; -struct mpv_event; -struct mpv_render_context; - -class LibMpvWidget : public QOpenGLWidget { - Q_OBJECT - - public: - explicit LibMpvWidget(QWidget* parent = nullptr, Qt::WindowFlags f = {}); - virtual ~LibMpvWidget(); - - void command(const QVariant& params); - void setProperty(const QString& name, const QVariant& value); - QVariant getProperty(const QString& name) const; - QSize sizeHint() const { - return QSize(480, 270); - } - - signals: - void durationChanged(int value); - void positionChanged(int value); - - protected: - virtual void initializeGL(); - virtual void paintGL(); - - private slots: - void on_mpv_events(); - void maybeUpdate(); - - private: - void handle_mpv_event(mpv_event* event); - static void on_update(void* ctx); - - private: - mpv_handle* mpv; - mpv_render_context* mpv_gl; - - // QWidget interface - protected: - virtual void keyPressEvent(QKeyEvent* event); - - // QObject interface - public: - virtual bool eventFilter(QObject* watched, QEvent* event); -}; - -#endif // LIBMPVWIDGET_H diff --git a/src/librssguard/gui/settings/settingsmediaplayer.cpp b/src/librssguard/gui/settings/settingsmediaplayer.cpp index b1c207175..01064f1a3 100644 --- a/src/librssguard/gui/settings/settingsmediaplayer.cpp +++ b/src/librssguard/gui/settings/settingsmediaplayer.cpp @@ -23,7 +23,9 @@ void SettingsMediaPlayer::loadSettings() { false); #elif defined(ENABLE_MEDIAPLAYER_QTMULTIMEDIA) m_ui.m_txtBackend->setText(QSL("libmpv")); - m_ui.m_helpInfo->setHelpText(tr("You use lightweight QtMultimedia-based media player backend."), false); + m_ui.m_helpInfo->setHelpText(tr("You use lightweight QtMultimedia-based media player backend. If some videos do not " + "play, then you likely need to install some codec pack."), + false); #else m_ui.m_txtBackend->setText(tr("no backend installed")); m_ui.m_helpInfo->setHelpText(tr("You do not have any media player available. Media player is only supported on "