mirror of
https://github.com/mumble-voip/mumble.git
synced 2025-10-26 11:19:16 +00:00
PulseAudio: cork input when it is not required
When self-muted or deafened, "cork" the audio input. Corking instructs the audio source to stop producing audio samples which— when the user is muted—are not needed and would never be transmitted. Without samples to process, the input DSP doesn't run. Corking can halve mumble's CPU consumption when muted, but your mileage may vary. This patch adds the MainWindow::corkAudioInputStream() signal to request changes in the corking state. Other audio backends could be modified to connect to this signal.
This commit is contained in:
parent
5a4f5297a3
commit
7d0b933a7e
@ -36,6 +36,7 @@ AudioWizard::AudioWizard(QWidget *p) : QWizard(p) {
|
||||
bInit = true;
|
||||
bLastActive = false;
|
||||
g.bInAudioWizard = true;
|
||||
g.mw->onChangeMute();
|
||||
|
||||
ticker = new QTimer(this);
|
||||
ticker->setObjectName(QLatin1String("Ticker"));
|
||||
@ -398,6 +399,7 @@ void AudioWizard::reject() {
|
||||
ao->wipe();
|
||||
aosSource = NULL;
|
||||
g.bInAudioWizard = false;
|
||||
g.mw->onChangeMute();
|
||||
|
||||
QWizard::reject();
|
||||
}
|
||||
@ -433,6 +435,7 @@ void AudioWizard::accept() {
|
||||
g.bPosTest = false;
|
||||
restartAudio();
|
||||
g.bInAudioWizard = false;
|
||||
g.mw->onChangeMute();
|
||||
QWizard::accept();
|
||||
}
|
||||
|
||||
|
||||
@ -2306,6 +2306,7 @@ void MainWindow::on_qaAudioMute_triggered() {
|
||||
g.sh->setSelfMuteDeafState(g.s.bMute, g.s.bDeaf);
|
||||
}
|
||||
|
||||
onChangeMute();
|
||||
updateTrayIcon();
|
||||
}
|
||||
|
||||
@ -2342,6 +2343,7 @@ void MainWindow::on_qaAudioDeaf_triggered() {
|
||||
g.sh->setSelfMuteDeafState(g.s.bMute, g.s.bDeaf);
|
||||
}
|
||||
|
||||
onChangeMute();
|
||||
updateTrayIcon();
|
||||
}
|
||||
|
||||
@ -2790,6 +2792,15 @@ void MainWindow::whisperReleased(QVariant scdata) {
|
||||
updateTarget();
|
||||
}
|
||||
|
||||
void MainWindow::onChangeMute()
|
||||
{
|
||||
if (!g.ai) {
|
||||
return;
|
||||
}
|
||||
|
||||
emit corkAudioInputStream(g.s.bMute && !g.bInAudioWizard);
|
||||
}
|
||||
|
||||
void MainWindow::onResetAudio()
|
||||
{
|
||||
qWarning("MainWindow: Start audio reset");
|
||||
@ -2849,6 +2860,7 @@ void MainWindow::serverConnected() {
|
||||
|
||||
if (g.s.bMute || g.s.bDeaf) {
|
||||
g.sh->setSelfMuteDeafState(g.s.bMute, g.s.bDeaf);
|
||||
onChangeMute();
|
||||
}
|
||||
|
||||
// Update QActions and menues
|
||||
|
||||
@ -269,6 +269,9 @@ class MainWindow : public QMainWindow, public MessageHandler, public Ui::MainWin
|
||||
void pttReleased();
|
||||
void whisperReleased(QVariant scdata);
|
||||
void onResetAudio();
|
||||
/// Called whenever the self-mute state may have changed. Dispatches
|
||||
/// corkAudioInputStream() if the desire for audio input has changed.
|
||||
void onChangeMute();
|
||||
void showRaiseWindow();
|
||||
void on_qaFilterToggle_triggered();
|
||||
/// Opens a save dialog for the image referenced by qtcSaveImageCursor.
|
||||
@ -279,7 +282,16 @@ class MainWindow : public QMainWindow, public MessageHandler, public Ui::MainWin
|
||||
/// Updates the user's image directory to the given path (any included
|
||||
/// filename is discarded).
|
||||
void updateImagePath(QString filepath) const;
|
||||
|
||||
signals:
|
||||
/// Reports that audio input is now, or is no longer, required.
|
||||
///
|
||||
/// Signal allows an \ref AudioInput to suspend the input stream
|
||||
/// when it is not required.
|
||||
///
|
||||
/// @param cork If true, the audio backend MAY now cork/suspend
|
||||
/// the input stream. If false, the audio backend MUST immediately
|
||||
/// un-cork/resume the stream.
|
||||
void corkAudioInputStream(const bool cork);
|
||||
public:
|
||||
MainWindow(QWidget *parent);
|
||||
~MainWindow() Q_DECL_OVERRIDE;
|
||||
|
||||
@ -301,6 +301,11 @@ void PulseAudioSystem::eventCallback(pa_mainloop_api *api, pa_defer_event *) {
|
||||
qsInputCache = idev;
|
||||
|
||||
pa_stream_connect_record(pasInput, qPrintable(idev), &buff, PA_STREAM_ADJUST_LATENCY);
|
||||
|
||||
// Ensure stream is initially un-muted
|
||||
pa_stream_cork(pasInput, 0, NULL, NULL);
|
||||
|
||||
connect(g.mw, &MainWindow::corkAudioInputStream, this, &PulseAudioSystem::corkAudioInputStream);
|
||||
}
|
||||
}
|
||||
|
||||
@ -371,6 +376,15 @@ void PulseAudioSystem::eventCallback(pa_mainloop_api *api, pa_defer_event *) {
|
||||
}
|
||||
}
|
||||
|
||||
void PulseAudioSystem::corkAudioInputStream(const bool cork)
|
||||
{
|
||||
if (pasInput) {
|
||||
pa_threaded_mainloop_lock(pam);
|
||||
pa_stream_cork(pasInput, cork, nullptr, nullptr);
|
||||
pa_threaded_mainloop_unlock(pam);
|
||||
}
|
||||
}
|
||||
|
||||
void PulseAudioSystem::context_state_callback(pa_context *c, void *userdata) {
|
||||
PulseAudioSystem *pas = reinterpret_cast<PulseAudioSystem *>(userdata);
|
||||
pas->contextCallback(c);
|
||||
|
||||
@ -80,6 +80,9 @@ class PulseAudioSystem : public QObject {
|
||||
void setVolumes();
|
||||
PulseAttenuation* getAttenuation(QString stream_restore_id);
|
||||
|
||||
public slots:
|
||||
void corkAudioInputStream(const bool cork);
|
||||
|
||||
public:
|
||||
QHash<QString, QString> qhInput;
|
||||
QHash<QString, QString> qhOutput;
|
||||
|
||||
@ -479,6 +479,7 @@ int main(int argc, char **argv) {
|
||||
g.p->rescanPlugins();
|
||||
|
||||
Audio::start();
|
||||
g.mw->onChangeMute();
|
||||
|
||||
a.setQuitOnLastWindowClosed(false);
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user