1 #include "raopservice.h"
7 audio_init(void *cls
, void **session
, int bits
, int channels
, int samplerate
)
9 QMetaObject::invokeMethod((QObject
*)cls
, "audioInit", Qt::BlockingQueuedConnection
,
10 Q_ARG(void*, (void*)session
),
13 Q_ARG(int, samplerate
));
17 audio_set_volume(void *cls
, void *session
, float volume
)
19 QMetaObject::invokeMethod((QObject
*)cls
, "audioSetVolume", Qt::BlockingQueuedConnection
,
20 Q_ARG(void*, session
),
21 Q_ARG(float, volume
));
25 audio_process(void *cls
, void *session
, const void *buffer
, int buflen
)
27 QMetaObject::invokeMethod((QObject
*)cls
, "audioProcess", Qt::BlockingQueuedConnection
,
28 Q_ARG(void*, session
),
29 Q_ARG(void*, (void*)buffer
),
34 audio_flush(void *cls
, void *session
)
36 QMetaObject::invokeMethod((QObject
*)cls
, "audioFlush", Qt::BlockingQueuedConnection
,
37 Q_ARG(void*, session
));
41 audio_destroy(void *cls
, void *session
)
43 QMetaObject::invokeMethod((QObject
*)cls
, "audioDestroy", Qt::BlockingQueuedConnection
,
44 Q_ARG(void*, session
));
47 RaopService::RaopService(QObject
*parent
) :
52 /* This whole hack is required because QAudioOutput
53 * needs to be created in a QThread, threads created
54 * outside Qt are not allowed (they have no eventloop) */
55 m_handler
.moveToThread(&m_thread
);
58 RaopService::~RaopService()
62 dnssd_destroy(m_dnssd
);
66 bool RaopService::init()
68 const char hwaddr
[] = { 0x48, 0x5d, 0x60, 0x7c, 0xee, 0x22 };
69 raop_callbacks_t raop_cbs
;
72 raop_cbs
.cls
= &m_handler
;
73 raop_cbs
.audio_init
= audio_init
;
74 raop_cbs
.audio_set_volume
= audio_set_volume
;
75 raop_cbs
.audio_process
= audio_process
;
76 raop_cbs
.audio_flush
= audio_flush
;
77 raop_cbs
.audio_destroy
= audio_destroy
;
79 QFile
file("airport.key");
81 // This is used when running from Qt Creator on Mac
82 file
.setFileName("../../../../airport.key");
85 // This is used when running from Qt Creator on Windows
86 file
.setFileName("../airport.key");
91 file
.open(QIODevice::ReadOnly
);
92 QByteArray array
= file
.read(file
.size());
95 m_raop
= raop_init(&raop_cbs
, array
.data(), hwaddr
, sizeof(hwaddr
));
100 m_dnssd
= dnssd_init(hwaddr
, sizeof(hwaddr
), &error
);
102 raop_destroy(m_raop
);
110 bool RaopService::start(const QString
& name
, quint16 port
)
112 if (!m_raop
|| !m_dnssd
|| m_thread
.isRunning()) {
117 if (raop_start(m_raop
, &port
) < 0) {
122 if (dnssd_register_raop(m_dnssd
, name
.toUtf8(), port
) < 0) {
132 void RaopService::stop()
135 dnssd_unregister_raop(m_dnssd
);
140 if (m_thread
.isRunning()) {