summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRoman Savochenko <roman@home.home>2023-11-19 10:20:26 +0200
committerRoman Savochenko <roman@home.home>2023-11-19 10:20:26 +0200
commit7173de9b1d76aada67d30573b764579a818ac684 (patch)
tree25afc726aa67b0ecd29b82f9066efb8a7809295e
parent268aed5464ce7c432e3c7320495e3767d8381a2b (diff)
downloadtdemultimedia-feat/kmix-dyn.tar.gz
tdemultimedia-feat/kmix-dyn.zip
KMix: Dynamism in tracing of appearance new audio-controllersfeat/kmix-dyn
Signed-off-by: Roman Savochenko <roman@home.home>
-rw-r--r--kmix/kmix.cpp39
-rw-r--r--kmix/kmix.h4
-rw-r--r--kmix/kmixapplet.cpp3
-rw-r--r--kmix/kmixctrl.cpp3
-rw-r--r--kmix/mixer.cpp2
-rw-r--r--kmix/mixer.h1
-rw-r--r--kmix/mixer_alsa9.cpp39
-rw-r--r--kmix/mixertoolbox.cpp25
-rw-r--r--kmix/mixertoolbox.h26
9 files changed, 120 insertions, 22 deletions
diff --git a/kmix/kmix.cpp b/kmix/kmix.cpp
index 20e9c58f..bdc2c521 100644
--- a/kmix/kmix.cpp
+++ b/kmix/kmix.cpp
@@ -4,6 +4,7 @@
* Copyright (C) 2000 Stefan Schimanski <schimmi@kde.org>
* Copyright (C) 2001 Preston Brown <pbrown@kde.org>
* Copyright (C) 2003 Sven Leiber <s.leiber@web.de>
+ * Copyright (C) 2020 Roman Savochenko <roman@oscada.org>
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
@@ -98,12 +99,18 @@ KMixWindow::KMixWindow()
hide();
}
connect( kapp, TQT_SIGNAL( aboutToQuit()), TQT_SLOT( saveSettings()) );
+
+ mixersUpdTimer = new TQTimer();
+ connect(mixersUpdTimer, TQT_SIGNAL(timeout()), this, TQT_SLOT(mixersUpdate()));
+ mixersUpdTimer->start(10000);
}
KMixWindow::~KMixWindow()
{
- MixerToolBox::deinitMixer();
+ delete mixersUpdTimer;
+
+ MixerToolBox::deinitMixer(Mixer::mixers());
}
@@ -137,6 +144,34 @@ KMixWindow::initActions()
}
void
+KMixWindow::mixersUpdate()
+{
+ //Do not update the mixers at the mixer window and the dock widget visibility
+ if(!m_dockWidget || isVisible() || (m_dockWidget->_dockAreaPopup && ((TQWidget*)m_dockWidget->_dockAreaPopup)->isVisible())) return;
+ //Detection the mixers configuration change
+ else {
+ TQPtrList<Mixer> tmpMix;
+#ifdef WITH_KMIX_EXPERIMENTAL
+ MixerToolBox::initMixer(tmpMix, KMixSettings::multiDriver(), m_hwInfoString, true);
+#else
+ MixerToolBox::initMixer(tmpMix, false, m_hwInfoString, true);
+#endif
+ bool chMixers = (tmpMix.count() != Mixer::mixers().count());
+ MixerToolBox::deinitMixer(tmpMix);
+ if(!chMixers) return;
+ }
+ MixerToolBox::deinitMixer(Mixer::mixers());
+#ifdef WITH_KMIX_EXPERIMENTAL
+ MixerToolBox::initMixer(Mixer::mixers(), KMixSettings::multiDriver(), m_hwInfoString);
+#else
+ MixerToolBox::initMixer(Mixer::mixers(), false, m_hwInfoString);
+#endif
+
+ initMixerWidgets();
+ updateDocking();
+}
+
+void
KMixWindow::initWidgets()
{
// Main widget and layout
@@ -271,6 +306,8 @@ void
KMixWindow::initMixerWidgets()
{
m_mixerWidgets.clear();
+ m_cMixer->clear();
+ mixerNameLayout->show();
int id=0;
Mixer *mixer;
diff --git a/kmix/kmix.h b/kmix/kmix.h
index 602102b5..64a5ad09 100644
--- a/kmix/kmix.h
+++ b/kmix/kmix.h
@@ -3,6 +3,7 @@
*
*
* Copyright (C) 2000 Stefan Schimanski <1Stein@gmx.de>
+ * Copyright (C) 2020 Roman Savochenko <roman@oscada.org>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
@@ -30,6 +31,7 @@
// include files for TQt
#include <tqstring.h>
#include <tqmap.h>
+#include <tqtimer.h>
class TQHBox;
class TQWidgetStack;
@@ -128,9 +130,11 @@ KMixWindow : public TDEMainWindow, virtual public KMixIface
KMixDockWidget *m_dockWidget;
TQString m_hwInfoString;
TQVBoxLayout *widgetsLayout;
+ TQTimer *mixersUpdTimer;
private slots:
//void removeMixerWidget( KMixerWidget *mw );
+ void mixersUpdate();
void slotHWInfo();
void showSelectedMixer( int mixer );
void configureGlobalShortcuts();
diff --git a/kmix/kmixapplet.cpp b/kmix/kmixapplet.cpp
index a4770993..30810c69 100644
--- a/kmix/kmixapplet.cpp
+++ b/kmix/kmixapplet.cpp
@@ -4,6 +4,7 @@
*
* Copyright (C) 2000 Stefan Schimanski <schimmi@kde.org>
* Copyright (C) 2004 Christian Esken <esken@kde.org>
+ * Copyright (C) 2020 Roman Savochenko <roman@oscada.org>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
@@ -226,7 +227,7 @@ KMixApplet::~KMixApplet()
s_instCount--;
if ( s_instCount == 0)
{
- MixerToolBox::deinitMixer();
+ MixerToolBox::deinitMixer(Mixer::mixers());
}
*/
}
diff --git a/kmix/kmixctrl.cpp b/kmix/kmixctrl.cpp
index 9f6188c7..4cfa1281 100644
--- a/kmix/kmixctrl.cpp
+++ b/kmix/kmixctrl.cpp
@@ -2,6 +2,7 @@
* kmixctrl - kmix volume save/restore utility
*
* Copyright (C) 2000 Stefan Schimanski <1Stein@gmx.de>
+ * Copyright (C) 2020 Roman Savochenko <roman@oscada.org>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
@@ -84,7 +85,7 @@ extern "C" KDE_EXPORT int kdemain(int argc, char *argv[])
mixer->volumeSave( TDEGlobal::config() );
}
- MixerToolBox::deinitMixer();
+ MixerToolBox::deinitMixer(Mixer::mixers());
return 0;
}
diff --git a/kmix/mixer.cpp b/kmix/mixer.cpp
index 150b196d..b7bd2899 100644
--- a/kmix/mixer.cpp
+++ b/kmix/mixer.cpp
@@ -4,6 +4,7 @@
*
* Copyright (C) 1996-2004 Christian Esken - esken@kde.org
* 2002 Helio Chissini de Castro - helio@conectiva.com.br
+ * Copyright (C) 2017,2020 Roman Savochenko <roman@oscada.org>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
@@ -108,6 +109,7 @@ Mixer::~Mixer() {
// Close the mixer. This might also free memory, depending on the called backend method
close();
delete _pollingTimer;
+ delete _mixerBackend;
}
void Mixer::volumeSave( TDEConfig *config )
diff --git a/kmix/mixer.h b/kmix/mixer.h
index 2ec99a1e..40d303dd 100644
--- a/kmix/mixer.h
+++ b/kmix/mixer.h
@@ -6,6 +6,7 @@
* 1996-2000 Christian Esken <esken@kde.org>
* Sven Fischer <herpes@kawo2.rwth-aachen.de>
* 2002 - Helio Chissini de Castro <helio@conectiva.com.br>
+ * Copyright (C) 2017 Roman Savochenko <roman@oscada.org>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
diff --git a/kmix/mixer_alsa9.cpp b/kmix/mixer_alsa9.cpp
index 22303b43..29424226 100644
--- a/kmix/mixer_alsa9.cpp
+++ b/kmix/mixer_alsa9.cpp
@@ -6,6 +6,7 @@
*
* Copyright (C) 2002 Helio Chissini de Castro <helio@conectiva.com.br>
* 2004 Christian Esken <esken@kde.org>
+ * Copyright (C) 2020 Roman Savochenko <roman@oscada.org>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
@@ -107,11 +108,7 @@ Mixer_ALSA::open()
snd_ctl_t *ctl_handle;
snd_ctl_card_info_t *hw_info;
- snd_ctl_card_info_alloca(&hw_info);
-
- snd_mixer_elem_t *elem;
- snd_mixer_selem_id_t *sid;
- snd_mixer_selem_id_alloca( &sid );
+ snd_ctl_card_info_malloc(&hw_info);
// Card information
if ((unsigned)m_devnum > 31) m_devnum = -1;
@@ -126,6 +123,7 @@ Mixer_ALSA::open()
{
kdDebug(67100) << probeMessage << "not found: snd_ctl_open err=" << snd_strerror(err) << endl;
//_stateMessage = errorText( Mixer::ERR_NODEV );
+ snd_ctl_card_info_free(hw_info);
return Mixer::ERR_OPEN;
}
@@ -134,6 +132,7 @@ Mixer_ALSA::open()
kdDebug(67100) << probeMessage << "not found: snd_ctl_card_info err=" << snd_strerror(err) << endl;
//_stateMessage = errorText( Mixer::ERR_READ );
snd_ctl_close( ctl_handle );
+ snd_ctl_card_info_free(hw_info);
return Mixer::ERR_READ;
}
@@ -155,6 +154,7 @@ Mixer_ALSA::open()
kdDebug(67100) << probeMessage << "not found: snd_mixer_open err=" << snd_strerror(err) << endl;
//errormsg( Mixer::ERR_NODEV );
_handle = 0;
+ snd_ctl_card_info_free(hw_info);
return Mixer::ERR_NODEV; // if we cannot open the mixer, we have no devices
}
//kdDebug(67100) << "OUT Mixer_ALSA snd_mixer_open()" << endl;
@@ -163,6 +163,8 @@ Mixer_ALSA::open()
{
kdDebug(67100) << probeMessage << "not found: snd_mixer_attach err=" << snd_strerror(err) << endl;
//errormsg( Mixer::ERR_PERM );
+ close();
+ snd_ctl_card_info_free(hw_info);
return Mixer::ERR_OPEN;
}
@@ -170,6 +172,8 @@ Mixer_ALSA::open()
{
kdDebug(67100) << probeMessage << "not found: snd_mixer_selem_register err=" << snd_strerror(err) << endl;
//errormsg( Mixer::ERR_READ );
+ close();
+ snd_ctl_card_info_free(hw_info);
return Mixer::ERR_READ;
}
@@ -178,11 +182,15 @@ Mixer_ALSA::open()
kdDebug(67100) << probeMessage << "not found: snd_mixer_load err=" << snd_strerror(err) << endl;
//errormsg( Mixer::ERR_READ );
close();
+ snd_ctl_card_info_free(hw_info);
return Mixer::ERR_READ;
}
kdDebug(67100) << probeMessage << "found" << endl;
+ snd_mixer_elem_t *elem;
+ snd_mixer_selem_id_t *sid;
+
unsigned int mixerIdx = 0;
for ( elem = snd_mixer_first_elem( _handle ); elem; elem = snd_mixer_elem_next( elem ), mixerIdx++ )
{
@@ -195,8 +203,7 @@ Mixer_ALSA::open()
continue;
}
-
- sid = (snd_mixer_selem_id_t*)malloc(snd_mixer_selem_id_sizeof()); // I believe *we* must malloc it for ourself
+ snd_mixer_selem_id_malloc( &sid );
snd_mixer_selem_get_id( elem, sid );
bool canPlay = false;
@@ -359,6 +366,8 @@ Mixer_ALSA::open()
}
if( !found )
{
+ close();
+ snd_ctl_card_info_free(hw_info);
return Mixer::ERR_INCOMPATIBLESET;
}
} // !virginOpen
@@ -372,6 +381,8 @@ Mixer_ALSA::open()
***************************************************************************************/
if ( !validDevice )
{
+ close();
+ snd_ctl_card_info_free(hw_info);
return Mixer::ERR_NODEV;
}
@@ -385,6 +396,8 @@ Mixer_ALSA::open()
/* setup for select on stdin and the mixer fd */
if ((m_count = snd_mixer_poll_descriptors_count(_handle)) < 0) {
kdDebug(67100) << "Mixer_ALSA::poll() , snd_mixer_poll_descriptors_count() err=" << m_count << "\n";
+ close();
+ snd_ctl_card_info_free(hw_info);
return Mixer::ERR_OPEN;
}
@@ -393,19 +406,27 @@ Mixer_ALSA::open()
m_fds = (struct pollfd*)calloc(m_count, sizeof(struct pollfd));
if (m_fds == NULL) {
kdDebug(67100) << "Mixer_ALSA::poll() , calloc() = null" << "\n";
+ close();
+ snd_ctl_card_info_free(hw_info);
return Mixer::ERR_OPEN;
}
m_fds->events = POLLIN;
if ((err = snd_mixer_poll_descriptors(_handle, m_fds, m_count)) < 0) {
kdDebug(67100) << "Mixer_ALSA::poll() , snd_mixer_poll_descriptors_count() err=" << err << "\n";
+ close();
+ snd_ctl_card_info_free(hw_info);
return Mixer::ERR_OPEN;
}
if (err != m_count) {
kdDebug(67100) << "Mixer_ALSA::poll() , snd_mixer_poll_descriptors_count() err=" << err << " m_count=" << m_count << "\n";
+ close();
+ snd_ctl_card_info_free(hw_info);
return Mixer::ERR_OPEN;
}
+ snd_ctl_card_info_free(hw_info);
+
return 0;
}
@@ -462,6 +483,10 @@ Mixer_ALSA::close()
}
+ for(int iMS = 0; iMS < mixer_sid_list.count(); iMS++)
+ if(mixer_sid_list[iMS])
+ snd_mixer_selem_id_free(mixer_sid_list[iMS]);
+
mixer_elem_list.clear();
mixer_sid_list.clear();
m_mixDevices.clear();
diff --git a/kmix/mixertoolbox.cpp b/kmix/mixertoolbox.cpp
index 4a19673b..f91fe9ad 100644
--- a/kmix/mixertoolbox.cpp
+++ b/kmix/mixertoolbox.cpp
@@ -3,6 +3,7 @@
*
*
* Copyright (C) 2004 Christian Esken <esken@kde.org>
+ * Copyright (C) 2017,2020 Roman Savochenko <roman@oscada.org>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
@@ -64,7 +65,7 @@ extern MixerFactory g_mixerFactories[];
* 'true' means to scan all backends. 'false' means: After scanning the
* current backend the next backend is only scanned if no Mixers were found yet.
*/
-void MixerToolBox::initMixer(TQPtrList<Mixer> &mixers, bool multiDriverMode, TQString& ref_hwInfoString)
+void MixerToolBox::initMixer(TQPtrList<Mixer> &mixers, bool multiDriverMode, TQString& ref_hwInfoString, bool isLight)
{
//kdDebug(67100) << "IN MixerToolBox::initMixer()"<<endl;
@@ -115,12 +116,13 @@ void MixerToolBox::initMixer(TQPtrList<Mixer> &mixers, bool multiDriverMode, TQS
// approach doesn't work for the one or other user.
int devNumMax = 19;
getDevIteratorFunc* f = g_mixerFactories[drv].getDevIterator;
- for( DevIterator* I = f ? f() : new DevIterator(); !I->end(); I->next())
+ DevIterator *I = f ? f() : new DevIterator();
+ for( ; !I->end(); I->next())
{
int dev = I->getdev();
Mixer *mixer = new Mixer( drv, dev );
if ( mixer->isValid() ) {
- mixer->open();
+ if(!isLight) mixer->open();
Mixer* m;
if (dev >= 0) {
for (m = mixers.first(); m; m = mixers.next())
@@ -131,7 +133,7 @@ void MixerToolBox::initMixer(TQPtrList<Mixer> &mixers, bool multiDriverMode, TQS
if (mixer->devnum() == m->devnum())
#endif
break;
- if (m) continue;
+ if (m) { delete mixer; continue; }
}
mixers.append( mixer );
// Count mixer nums for every mixer name to identify mixers with equal names.
@@ -145,6 +147,7 @@ void MixerToolBox::initMixer(TQPtrList<Mixer> &mixers, bool multiDriverMode, TQS
* %2, the mixer name, is typically coming from an OS driver. It could contain colons.
* %3, the mixer number, is a number: it does not contain colons.
*/
+ if(!isLight) {
TQString mixerName = mixer->mixerName();
mixerName.replace(":","_");
TQString primaryKeyOfMixer = TQString("%1::%2:%3")
@@ -158,6 +161,7 @@ void MixerToolBox::initMixer(TQPtrList<Mixer> &mixers, bool multiDriverMode, TQS
primaryKeyOfMixer.replace("=","_");
mixer->setID(primaryKeyOfMixer);
+ }
} // valid
else
@@ -174,7 +178,7 @@ void MixerToolBox::initMixer(TQPtrList<Mixer> &mixers, bool multiDriverMode, TQS
else {
// In No-multiDriver-mode we only need to check after we reached devNumMax
if ( dev == devNumMax ) {
- if ( Mixer::mixers().count() != 0 ) {
+ if ( mixers.count() != 0 ) {
// highest device number of driver and a Mixer => finished
autodetectionFinished = true;
}
@@ -182,7 +186,7 @@ void MixerToolBox::initMixer(TQPtrList<Mixer> &mixers, bool multiDriverMode, TQS
} // !multiDriver
// append driverName (used drivers)
- if ( !drvInfoAppended )
+ if ( !drvInfoAppended && !isLight )
{
drvInfoAppended = true;
TQString driverName = Mixer::driverName(drv);
@@ -211,9 +215,10 @@ void MixerToolBox::initMixer(TQPtrList<Mixer> &mixers, bool multiDriverMode, TQS
} // !multipleDriversActive
} // loop over sound card devices of current driver
+ delete I;
} // loop over soundcard drivers
- if (Mixer::masterCard() == 0)
+ if (Mixer::masterCard() == 0 && !isLight)
{
// We have no master card yet. This actually only happens when there was
// not one defined in the kmixrc.
@@ -252,15 +257,15 @@ void MixerToolBox::initMixer(TQPtrList<Mixer> &mixers, bool multiDriverMode, TQS
/*
* Clean up and free all ressources of all found Mixers, which were found in the initMixer() call
*/
-void MixerToolBox::deinitMixer()
+void MixerToolBox::deinitMixer(TQPtrList<Mixer> &mixers)
{
//kdDebug(67100) << "IN MixerToolBox::deinitMixer()"<<endl;
Mixer *mixer;
- while ( (mixer=Mixer::mixers().first()) != 0)
+ while ( (mixer=mixers.first()) != 0)
{
//kdDebug(67100) << "MixerToolBox::deinitMixer() Remove Mixer" << endl;
mixer->close();
- Mixer::mixers().remove(mixer);
+ mixers.remove(mixer);
delete mixer;
}
// kdDebug(67100) << "OUT MixerToolBox::deinitMixer()"<<endl;
diff --git a/kmix/mixertoolbox.h b/kmix/mixertoolbox.h
index 884471ef..2cceeef3 100644
--- a/kmix/mixertoolbox.h
+++ b/kmix/mixertoolbox.h
@@ -1,3 +1,25 @@
+/*
+ * KMix -- KDE's full featured mini mixer
+ *
+ *
+ * Copyright (C) 2004 Christian Esken <esken@kde.org>
+ * Copyright (C) 2020 Roman Savochenko <roman@oscada.org>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public
+ * License along with this program; if not, write to the Free
+ * Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ */
+
#ifndef MIXERTOOLBOX_H
#define MIXERTOOLBOX_H
@@ -14,8 +36,8 @@ class Mixer;
*/
class MixerToolBox {
public:
- static void initMixer(TQPtrList<Mixer>&, bool, TQString&);
- static void deinitMixer();
+ static void initMixer(TQPtrList<Mixer>&, bool, TQString&, bool isLight = false);
+ static void deinitMixer(TQPtrList<Mixer>&);
};