From d09a3cbc60da86f57d06477dea1a57962a11ffb2 Mon Sep 17 00:00:00 2001 From: Mladen Milinkovic Date: Mon, 8 Jul 2019 20:19:03 +0200 Subject: [PATCH] MPV player config options aren't hardcoded anymore. --- src/videoplayerplugins/mpv/mpvbackend.cpp | 37 ++++++- src/videoplayerplugins/mpv/mpvbackend.h | 8 +- .../mpv/mpvconfigwidget.cpp | 102 ++++++++++++++++-- src/videoplayerplugins/mpv/mpvconfigwidget.h | 8 ++ 4 files changed, 139 insertions(+), 16 deletions(-) diff --git a/src/videoplayerplugins/mpv/mpvbackend.cpp b/src/videoplayerplugins/mpv/mpvbackend.cpp index d85a56c..9fdcd95 100644 --- a/src/videoplayerplugins/mpv/mpvbackend.cpp +++ b/src/videoplayerplugins/mpv/mpvbackend.cpp @@ -33,8 +33,6 @@ #include using namespace SubtitleComposer; -using namespace mpv; -using namespace mpv::qt; MPVBackend::MPVBackend() : PlayerBackend(), @@ -218,6 +216,37 @@ MPVBackend::mpvEventHandle(mpv_event *event) } } +static QVariant +node_to_variant(const mpv_node *node) +{ + switch(node->format) { + case MPV_FORMAT_STRING: + return QVariant(QString::fromUtf8(node->u.string)); + case MPV_FORMAT_FLAG: + return QVariant(static_cast(node->u.flag)); + case MPV_FORMAT_INT64: + return QVariant(static_cast(node->u.int64)); + case MPV_FORMAT_DOUBLE: + return QVariant(node->u.double_); + case MPV_FORMAT_NODE_ARRAY: { + mpv_node_list *list = node->u.list; + QVariantList qlist; + for(int n = 0; n < list->num; n++) + qlist.append(node_to_variant(&list->values[n])); + return QVariant(qlist); + } + case MPV_FORMAT_NODE_MAP: { + mpv_node_list *list = node->u.list; + QVariantMap qmap; + for(int n = 0; n < list->num; n++) + qmap.insert(QString::fromUtf8(list->keys[n]), node_to_variant(&list->values[n])); + return QVariant(qmap); + } + default: // MPV_FORMAT_NONE, unknown values (e.g. future extensions) + return QVariant(); + } +} + void MPVBackend::updateTextData(const mpv_event_property *prop) { @@ -230,7 +259,7 @@ MPVBackend::updateTextData(const mpv_event_property *prop) if(val.format != MPV_FORMAT_NODE_MAP) continue; - const QMap &map = mpv::qt::node_to_variant(&val).toMap(); + const QMap &map = node_to_variant(&val).toMap(); if(map[QStringLiteral("type")].toString() != QStringLiteral("sub") || map[QStringLiteral("external")].toBool() == true) @@ -269,7 +298,7 @@ MPVBackend::updateAudioData(const mpv_event_property *prop) if(val.format != MPV_FORMAT_NODE_MAP) continue; - const QMap &map = mpv::qt::node_to_variant(&val).toMap(); + const QMap &map = node_to_variant(&val).toMap(); if(map[QStringLiteral("type")].toString() != QStringLiteral("audio")) continue; diff --git a/src/videoplayerplugins/mpv/mpvbackend.h b/src/videoplayerplugins/mpv/mpvbackend.h index d0edf2e..5e19fa1 100644 --- a/src/videoplayerplugins/mpv/mpvbackend.h +++ b/src/videoplayerplugins/mpv/mpvbackend.h @@ -23,7 +23,7 @@ #include "videoplayer/playerbackend.h" -#include +#include #include #include @@ -76,14 +76,10 @@ signals: protected slots: void onMPVEvents(); -protected: - void setupProcessArgs(const QString &filePath); - +private: void mpvEventHandle(mpv_event *event); - static void wakeup(void *ctx); -private: void updateTextData(const mpv_event_property *prop); void updateAudioData(const mpv_event_property *prop); void updateVideoData(); diff --git a/src/videoplayerplugins/mpv/mpvconfigwidget.cpp b/src/videoplayerplugins/mpv/mpvconfigwidget.cpp index 78458f8..6958141 100644 --- a/src/videoplayerplugins/mpv/mpvconfigwidget.cpp +++ b/src/videoplayerplugins/mpv/mpvconfigwidget.cpp @@ -20,6 +20,11 @@ #include "mpvconfigwidget.h" +#include +#include + +#include "scconfig.h" + using namespace SubtitleComposer; MPVConfigWidget::MPVConfigWidget(QWidget *parent) @@ -27,14 +32,99 @@ MPVConfigWidget::MPVConfigWidget(QWidget *parent) { setupUi(this); - kcfg_mpvVideoOutput->addItems(QString("vdpau vaapi opengl opengl-hq sdl xv wayland x11 null").split(' ')); - kcfg_mpvVideoOutput->setProperty("kcfg_property", QByteArray("currentText")); + // FIXME: libmpv requires LC_NUMERIC category to be set to "C".. is there some nicer way to do this? + std::setlocale(LC_NUMERIC, "C"); + m_mpv = mpv_create(); + mpv_request_log_messages(m_mpv, "info"); + if(mpv_initialize(m_mpv) >= 0) { + getHelpResponse(); // make sure there are no log messages + static QStringList bad = { + QStringLiteral("libmpv"), + QStringLiteral("null"), + QStringLiteral("image"), + QStringLiteral("tct"), + QStringLiteral("caca"), + QStringLiteral("pcm"), + }; + + mpv_set_property_string(m_mpv, "vo", "help"); + for(QString row : getHelpResponse()) { + int pos = row.indexOf(QChar(' ')); + if(pos == -1) + continue; + const QString name = row.left(pos); + if(bad.contains(name)) + continue; + row.insert(pos, "\t-"); + if(SCConfig::mpvVideoOutput() == name) + kcfg_mpvVideoOutput->setCurrentIndex(kcfg_mpvHwDecode->count()); + kcfg_mpvVideoOutput->addItem(row, name); + } + kcfg_mpvVideoOutput->setProperty("kcfg_property", QByteArray("currentData")); + + mpv_set_property_string(m_mpv, "hwdec", "help"); + kcfg_mpvHwDecode->addItem(QStringLiteral("auto\t- Choose best HW decoder"), QStringLiteral("auto")); + for(QString row : getHelpResponse()) { + int pos = row.indexOf(QChar(' ')); + if(pos == -1) + continue; + const QString name = row.left(pos); + const QString lastName = kcfg_mpvHwDecode->itemData(kcfg_mpvHwDecode->count() - 1).toString(); + if(lastName == name || bad.contains(name)) + continue; + if(SCConfig::mpvHwDecode() == name) + kcfg_mpvHwDecode->setCurrentIndex(kcfg_mpvHwDecode->count()); + kcfg_mpvHwDecode->addItem(name, name); + } + kcfg_mpvHwDecode->setProperty("kcfg_property", QByteArray("currentData")); + + mpv_set_property_string(m_mpv, "ao", "help"); + for(QString row : getHelpResponse()) { + int pos = row.indexOf(QChar(' ')); + if(pos == -1) + continue; + const QString name = row.left(pos); + if(bad.contains(name)) + continue; + row.insert(pos, "\t-"); + if(SCConfig::mpvAudioOutput() == name) + kcfg_mpvAudioOutput->setCurrentIndex(kcfg_mpvHwDecode->count()); + kcfg_mpvAudioOutput->addItem(row, name); + } + kcfg_mpvAudioOutput->setProperty("kcfg_property", QByteArray("currentData")); - kcfg_mpvHwDecode->addItems(QString("auto vdpau vaapi vaapi-copy").split(' ')); - kcfg_mpvHwDecode->setProperty("kcfg_property", QByteArray("currentText")); + mpv_detach_destroy(m_mpv); + } else { + kcfg_mpvVideoOutput->addItems(QString("vdpau vaapi opengl opengl-hq sdl xv wayland x11 null").split(' ')); + kcfg_mpvVideoOutput->setProperty("kcfg_property", QByteArray("currentText")); - kcfg_mpvAudioOutput->addItems(QString("pulse alsa oss portaudio jack null").split(' ')); - kcfg_mpvAudioOutput->setProperty("kcfg_property", QByteArray("currentText")); + kcfg_mpvHwDecode->addItems(QString("auto vdpau vaapi vaapi-copy").split(' ')); + kcfg_mpvHwDecode->setProperty("kcfg_property", QByteArray("currentText")); + + kcfg_mpvAudioOutput->addItems(QString("pulse alsa oss portaudio jack null").split(' ')); + kcfg_mpvAudioOutput->setProperty("kcfg_property", QByteArray("currentText")); + } +} + +const QStringList +MPVConfigWidget::getHelpResponse() +{ + QStringList res; + while(m_mpv) { + mpv_event *event = mpv_wait_event(m_mpv, .1); + if(event->event_id == MPV_EVENT_LOG_MESSAGE) { + mpv_event_log_message *msg = reinterpret_cast(event->data); + if(msg->log_level == MPV_LOG_LEVEL_INFO && strcmp(msg->prefix, "cplayer") == 0) { + QString row = QString::fromUtf8(msg->text).simplified(); + if(row.endsWith(QChar(':'))) + continue; + res << row; + } + } else if(event->event_id == MPV_EVENT_NONE) { + break; + } + } + return res; } MPVConfigWidget::~MPVConfigWidget() diff --git a/src/videoplayerplugins/mpv/mpvconfigwidget.h b/src/videoplayerplugins/mpv/mpvconfigwidget.h index f4105d7..775b507 100644 --- a/src/videoplayerplugins/mpv/mpvconfigwidget.h +++ b/src/videoplayerplugins/mpv/mpvconfigwidget.h @@ -23,6 +23,8 @@ #include "ui_mpvconfigwidget.h" +#include + namespace SubtitleComposer { class MPVConfigWidget : public QWidget, private Ui::MPVConfigWidget { @@ -31,6 +33,12 @@ class MPVConfigWidget : public QWidget, private Ui::MPVConfigWidget public: explicit MPVConfigWidget(QWidget *parent = 0); virtual ~MPVConfigWidget(); + +private: + const QStringList getHelpResponse(); + +private: + mpv_handle *m_mpv; }; } -- 2.29.2