mastervolume: port to use the pipewire audiomixer service
[apps/homescreen.git] / homescreen / src / mastervolume.cpp
index 46985ee..5a6dc9a 100644 (file)
  */
 
 #include "mastervolume.h"
+#include <QJsonObject>
+#include <QTimer>
+#include <QtDebug>
 
-#include <QtCore/QDebug>
+MasterVolume::MasterVolume(QObject* parent)
+       : QObject(parent)
+       , m_volume{50}
+{
+       connect(&m_client, SIGNAL(connected()), this, SLOT(onClientConnected()));
+       connect(&m_client, SIGNAL(disconnected()), this, SLOT(onClientDisconnected()));
+       connect(&m_client, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(onClientError(QAbstractSocket::SocketError)));
+       connect(&m_client, SIGNAL(eventReceived(QString, const QJsonValue&)), this, SLOT(onClientEventReceived(QString, const QJsonValue&)));
+}
+
+void MasterVolume::open(const QUrl& url)
+{
+       m_url = url;
+       TryOpen();
+}
+
+qint32 MasterVolume::getVolume() const
+{
+       return m_volume;
+}
+
+void MasterVolume::setVolume(qint32 volume)
+{
+       if (m_volume != volume)
+       {
+               m_volume = volume;
+               QJsonObject arg;
+               arg.insert("control", "Master");
+               arg.insert("value", volume);
+               m_client.call("audiomixer", "volume", arg);
+       }
+}
 
-void MasterVolume::setVolume(pa_volume_t volume)
+void MasterVolume::onClientConnected()
 {
-       int volume_delta = volume - m_volume;
-       m_volume = volume;
-       emit sliderVolumeChanged(volume_delta);
+       QJsonObject arg;
+       arg.insert("control", "Master");
+       m_client.call("audiomixer", "volume", arg, [this](bool r, const QJsonValue& v) {
+               if (r && v.isObject()) {
+                       int volume = v.toObject()["response"].toObject()["volume"].toDouble() * 100;
+                       volume = qBound(0, volume, 100);
+                       if (m_volume != volume)
+                       {
+                               m_volume = volume;
+                               emit VolumeChanged();
+                       }
+               }
+
+               QJsonObject arg;
+               arg.insert("event", "volume_changed");
+               m_client.call("audiomixer", "subscribe", arg);
+       });
+}
+
+void MasterVolume::onClientDisconnected()
+{
+       qDebug() << "MasterVolume::onClientDisconnected!";
+       QTimer::singleShot(1000, this, SLOT(TryOpen()));
+}
+
+void MasterVolume::onClientError(QAbstractSocket::SocketError se)
+{
+       qDebug() << "MasterVolume::onClientError: " << se;
+}
+
+void MasterVolume::onClientEventReceived(QString name, const QJsonValue& data)
+{
+       qDebug() << "MasterVolume::onClientEventReceived[" << name << "]: " << data;
+       if (name == "audiomixer/volume_changed")
+       {
+               QString ctlName = data.toObject()["control"].toString();
+
+               if (ctlName != "Master")
+                       return;
 
+               int volume = data.toObject()["value"].toDouble() * 100;
+               volume = qBound(0, volume, 100);
+               if (m_volume != volume)
+               {
+                       m_volume = volume;
+                       emit VolumeChanged();
+               }
+       }
 }
 
-void MasterVolume::changeExternalVolume(int volume)
+void MasterVolume::TryOpen()
 {
-       m_volume = volume;
-       emit volumeChanged();
+       m_client.open(m_url);
 }