-rw-r--r-- | libopie2/README | 12 | ||||
-rw-r--r-- | libopie2/config.in | 1 | ||||
-rw-r--r-- | libopie2/examples/config.in | 6 | ||||
-rw-r--r-- | libopie2/examples/examples.pro | 2 | ||||
-rw-r--r-- | libopie2/examples/opiemm/.cvsignore | 6 | ||||
-rw-r--r-- | libopie2/examples/opiemm/opiemm.pro | 3 | ||||
-rw-r--r-- | libopie2/examples/opiemm/osoundsystemdemo/.cvsignore | 6 | ||||
-rw-r--r-- | libopie2/examples/opiemm/osoundsystemdemo/osoundsystemdemo.cpp | 32 | ||||
-rw-r--r-- | libopie2/examples/opiemm/osoundsystemdemo/osoundsystemdemo.pro | 12 | ||||
-rw-r--r-- | libopie2/libopie2.control | 2 | ||||
-rw-r--r-- | libopie2/libopie2.pro | 2 | ||||
-rw-r--r-- | libopie2/opiemm/.cvsignore | 6 | ||||
-rw-r--r-- | libopie2/opiemm/config.in | 7 | ||||
-rw-r--r-- | libopie2/opiemm/opiemm.pro | 16 | ||||
-rw-r--r-- | libopie2/opiemm/osoundsystem.cpp | 315 | ||||
-rw-r--r-- | libopie2/opiemm/osoundsystem.h | 216 |
16 files changed, 638 insertions, 6 deletions
diff --git a/libopie2/README b/libopie2/README index 5130290..57172a7 100644 --- a/libopie2/README +++ b/libopie2/README @@ -19,8 +19,9 @@ libopie is functionally seperated into the following libraries: - libopieui - libopiepim - libopiedb - libopienet + - libopiemm 1.1 Contents of libopiecore [ opiecore ] -------------------------------------------------------- @@ -131,8 +132,14 @@ USE THE CLASSES IN libopie/pim INSTEAD !(eilers) <libmail stuff> <libbend stuff> <libftp stuff> +1.6 Contents of libopiemm [ opiemm ] +-------------------------------------------------------- + + - osoundsystem + - oaudiointerface + - osoundserver -------------------------------------------------------- 2.0 Feature Description -------------------------------------------------------- @@ -154,4 +161,9 @@ USE THE CLASSES IN libopie/pim INSTEAD !(eilers) ... 2.5 libopienet +... + +2.6 libopiemm + +... diff --git a/libopie2/config.in b/libopie2/config.in index 7c4d9bb..5a0e443 100644 --- a/libopie2/config.in +++ b/libopie2/config.in @@ -3,8 +3,9 @@ menu "libopie2" source libopie2/opiedb/config.in source libopie2/opienet/config.in source libopie2/opiepim/config.in source libopie2/opieui/config.in + source libopie2/opiemm/config.in comment "" source libopie2/examples/config.in endmenu diff --git a/libopie2/examples/config.in b/libopie2/examples/config.in index d18e479..478a822 100644 --- a/libopie2/examples/config.in +++ b/libopie2/examples/config.in @@ -1,6 +1,6 @@ config LIBOPIE2EXAMPLES boolean "libopie2 examples" default "n" - depends ( LIBQPE || LIBQPE-X11 ) && LIBOPIE2CORE && LIBOPIE2NET && LIBOPIE2UI && LIBOPIE2PIM && LIBOPIE2UI - comment "the examples need a libqpe, libopie2core, libopie2db, libopie2net, libopie2pim and libopie2ui" - depends !(( LIBQPE || LIBQPE-X11 ) && LIBOPIE2CORE && LIBOPIE2NET && LIBOPIE2UI && LIBOPIE2PIM && LIBOPIE2UI) + depends ( LIBQPE || LIBQPE-X11 ) && LIBOPIE2CORE && LIBOPIE2NET && LIBOPIE2UI && LIBOPIE2PIM && LIBOPIE2UI && LIBOPIE2MM + comment "the examples need a libqpe, libopie2core, libopie2db, libopie2net, libopie2pim, libopie2ui and libopie2mm" + depends !(( LIBQPE || LIBQPE-X11 ) && LIBOPIE2CORE && LIBOPIE2NET && LIBOPIE2UI && LIBOPIE2PIM && LIBOPIE2UI && LIBOPIE2MM) diff --git a/libopie2/examples/examples.pro b/libopie2/examples/examples.pro index 2ae7eb7..8add40d 100644 --- a/libopie2/examples/examples.pro +++ b/libopie2/examples/examples.pro @@ -1,4 +1,4 @@ TEMPLATE = subdirs -unix:SUBDIRS = opieui opienet opiecore +unix:SUBDIRS = opieui opienet opiecore opiemm #include ( ../../../include.pro ) diff --git a/libopie2/examples/opiemm/.cvsignore b/libopie2/examples/opiemm/.cvsignore new file mode 100644 index 0000000..8f7300c --- a/dev/null +++ b/libopie2/examples/opiemm/.cvsignore @@ -0,0 +1,6 @@ +Makefile* +moc* +*moc +*.o +~* + diff --git a/libopie2/examples/opiemm/opiemm.pro b/libopie2/examples/opiemm/opiemm.pro new file mode 100644 index 0000000..0522ebe --- a/dev/null +++ b/libopie2/examples/opiemm/opiemm.pro @@ -0,0 +1,3 @@ +TEMPLATE = subdirs +SUBDIRS = osoundsystemdemo + diff --git a/libopie2/examples/opiemm/osoundsystemdemo/.cvsignore b/libopie2/examples/opiemm/osoundsystemdemo/.cvsignore new file mode 100644 index 0000000..8f7300c --- a/dev/null +++ b/libopie2/examples/opiemm/osoundsystemdemo/.cvsignore @@ -0,0 +1,6 @@ +Makefile* +moc* +*moc +*.o +~* + diff --git a/libopie2/examples/opiemm/osoundsystemdemo/osoundsystemdemo.cpp b/libopie2/examples/opiemm/osoundsystemdemo/osoundsystemdemo.cpp new file mode 100644 index 0000000..79bf327 --- a/dev/null +++ b/libopie2/examples/opiemm/osoundsystemdemo/osoundsystemdemo.cpp @@ -0,0 +1,32 @@ +#include <opie2/osoundsystem.h> + +int main( int argc, char** argv ) +{ + qDebug( "OPIE Sound System Demo" ); + + OSoundSystem* sound = OSoundSystem::instance(); + + OSoundSystem::CardIterator it = sound->iterator(); +/* + while ( it.current() ) + { + qDebug( "DEMO: OSoundSystem contains Interface '%s'", (const char*) it.current()->name() ); + ++it; + } + +*/ + OSoundCard* card = it.current(); + + OMixerInterface* mixer = card->mixer(); + + QStringList channels = mixer->allChannels(); + + for ( QStringList::Iterator it = channels.begin(); it != channels.end(); ++it ) + { + qDebug( "OSSDEMO: Mixer has channel %s", (const char*) *it ); + qDebug( "OSSDEMO: +--- volume %d (left) | %d (right)", mixer->volume( *it ) & 0xff, mixer->volume( *it ) >> 8 ); + } + + return 0; + +} diff --git a/libopie2/examples/opiemm/osoundsystemdemo/osoundsystemdemo.pro b/libopie2/examples/opiemm/osoundsystemdemo/osoundsystemdemo.pro new file mode 100644 index 0000000..ba66165 --- a/dev/null +++ b/libopie2/examples/opiemm/osoundsystemdemo/osoundsystemdemo.pro @@ -0,0 +1,12 @@ +TEMPLATE = app +CONFIG = qt warn_on debug +HEADERS = +SOURCES = osoundsystemdemo.cpp +INCLUDEPATH += $(OPIEDIR)/include +DEPENDPATH += $(OPIEDIR)/include +LIBS += -lopiecore2 -lopiemm2 +TARGET = osoundsystemdemo +MOC_DIR = moc +OBJECTS_DIR = obj + +include ( $(OPIEDIR)/include.pro ) diff --git a/libopie2/libopie2.control b/libopie2/libopie2.control index 0733bf4..cb5ada9 100644 --- a/libopie2/libopie2.control +++ b/libopie2/libopie2.control @@ -1,6 +1,6 @@ Package: libopie2 -Files: $OPIEDIR/lib/libopiecore2.so.1.8.1 $OPIEDIR/lib/libopiecore2.so.1.8 $OPIEDIR/lib/libopiecore2.so.1 $OPIEDIR/lib/libopienet2.so.1.8.1 $OPIEDIR/lib/libopienet2.so.1.8 $OPIEDIR/lib/libopienet2.so.1 $OPIEDIR/lib/libopieui2.so.1.8.1 $OPIEDIR/lib/libopieui2.so.1.8 $OPIEDIR/lib/libopieui2.so.1 $OPIEDIR/etc/manufacturers +Files: $OPIEDIR/lib/libopiecore2.so.* $OPIEDIR/lib/libopienet2.so.* $OPIEDIR/lib/libopieui2.so.* $OPIEDIR/lib/libopiemm2.so.* $OPIEDIR/etc/manufacturers Priority: optional Section: opie/system Maintainer: Opie Team <opie@handhelds.org> Architecture: arm diff --git a/libopie2/libopie2.pro b/libopie2/libopie2.pro index 0b52abc..0bd1d06 100644 --- a/libopie2/libopie2.pro +++ b/libopie2/libopie2.pro @@ -1,4 +1,4 @@ TEMPLATE = subdirs -unix:SUBDIRS = opiecore opiedb opiepim opieui opienet examples +unix:SUBDIRS = opiecore opiedb opiepim opieui opienet opiemm examples include ( $(OPIEDIR)/include.pro ) diff --git a/libopie2/opiemm/.cvsignore b/libopie2/opiemm/.cvsignore new file mode 100644 index 0000000..8f7300c --- a/dev/null +++ b/libopie2/opiemm/.cvsignore @@ -0,0 +1,6 @@ +Makefile* +moc* +*moc +*.o +~* + diff --git a/libopie2/opiemm/config.in b/libopie2/opiemm/config.in new file mode 100644 index 0000000..c95d14b --- a/dev/null +++ b/libopie2/opiemm/config.in @@ -0,0 +1,7 @@ + config LIBOPIE2MM + boolean "libopie2mm (audio and video related classes)" + default "n" + depends ( LIBQPE || LIBQPE-X11 ) && LIBOPIE2CORE + comment "libopie2mm needs a libqpe and libopie2core" + depends !(( LIBQPE || LIBQPE-X11 ) && LIBOPIE2CORE) + diff --git a/libopie2/opiemm/opiemm.pro b/libopie2/opiemm/opiemm.pro new file mode 100644 index 0000000..8e5eeb4 --- a/dev/null +++ b/libopie2/opiemm/opiemm.pro @@ -0,0 +1,16 @@ +TEMPLATE = lib +CONFIG += qt warn_on debug +DESTDIR = $(OPIEDIR)/lib +HEADERS = osoundsystem.h +SOURCES = osoundsystem.cpp +INTERFACES = +TARGET = opiemm2 +VERSION = 1.8.1 +INCLUDEPATH += $(OPIEDIR)/include +DEPENDPATH += $(OPIEDIR)/include +LIBS += +MOC_DIR = moc +OBJECTS_DIR = obj + +include ( $(OPIEDIR)/include.pro ) + diff --git a/libopie2/opiemm/osoundsystem.cpp b/libopie2/opiemm/osoundsystem.cpp new file mode 100644 index 0000000..fd23bea --- a/dev/null +++ b/libopie2/opiemm/osoundsystem.cpp @@ -0,0 +1,315 @@ +/* + This file is part of the Opie Project + + (C) 2003 Michael 'Mickey' Lauer <mickey@tm.informatik.uni-frankfurt.de> + =. + .=l. + .>+-= + _;:, .> :=|. This program is free software; you can +.> <`_, > . <= redistribute it and/or modify it under +:`=1 )Y*s>-.-- : the terms of the GNU Library General Public +.="- .-=="i, .._ License as published by the Free Software + - . .-<_> .<> Foundation; either version 2 of the License, + ._= =} : or (at your option) any later version. + .%`+i> _;_. + .i_,=:_. -<s. 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 library; see the file COPYING.LIB. + If not, write to the Free Software Foundation, + Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + +*/ + +#include <opie2/osoundsystem.h> + +#include <errno.h> +#include <fcntl.h> +#include <string.h> +#include <sys/ioctl.h> +#include <sys/types.h> +#include <sys/soundcard.h> +#include <sys/stat.h> + + +/*====================================================================================== + * OSoundSystem + *======================================================================================*/ + +OSoundSystem* OSoundSystem::_instance = 0; + +OSoundSystem::OSoundSystem() +{ + qDebug( "OSoundSystem::OSoundSystem()" ); + synchronize(); +} + +void OSoundSystem::synchronize() +{ + // gather available interfaces by inspecting /dev + //FIXME: we could use SIOCGIFCONF here, but we aren't interested in virtual (e.g. eth0:0) devices + //FIXME: Use SIOCGIFCONF anway, because we can disable listing of aliased devices + + _interfaces.clear(); + _interfaces.insert( "soundcard", new OSoundCard( this, "soundcard" ) ); + + + /* + + + + + QString str; + QFile f( "/dev/sound" ); + bool hasFile = f.open( IO_ReadOnly ); + if ( !hasFile ) + { + qDebug( "OSoundSystem: /dev/sound not existing. No sound devices available" ); + return; + } + QTextStream s( &f ); + s.readLine(); + s.readLine(); + while ( !s.atEnd() ) + { + s >> str; + str.truncate( str.find( ':' ) ); + qDebug( "OSoundSystem: found interface '%s'", (const char*) str ); + OAudioInterface* iface; + iface = new OAudioInterface( this, (const char*) str ); + + _interfaces.insert( str, iface ); + s.readLine(); + } +*/ +} + + +int OSoundSystem::count() const +{ + return _interfaces.count(); +} + + +OSoundCard* OSoundSystem::card( const QString& iface ) const +{ + return _interfaces[iface]; +} + + +OSoundSystem* OSoundSystem::instance() +{ + if ( !_instance ) _instance = new OSoundSystem(); + return _instance; +} + + +OSoundSystem::CardIterator OSoundSystem::iterator() const +{ + return OSoundSystem::CardIterator( _interfaces ); +} + + +/*====================================================================================== + * OSoundCard + *======================================================================================*/ + +OSoundCard::OSoundCard( QObject* parent, const char* name ) + :QObject( parent, name ), _audio( 0 ), _mixer( 0 ) +{ + qDebug( "OSoundCard::OSoundCard()" ); + init(); +} + + +OSoundCard::~OSoundCard() +{ +} + + +void OSoundCard::init() +{ + _audio = new OAudioInterface( this, "/dev/dsp" ); + _mixer = new OMixerInterface( this, "/dev/mixer" ); +} + + +/*====================================================================================== + * OAudioInterface + *======================================================================================*/ + +OAudioInterface::OAudioInterface( QObject* parent, const char* name ) + :QObject( parent, name ) +{ + qDebug( "OAudioInterface::OAudioInterface()" ); + init(); +} + + +OAudioInterface::~OAudioInterface() +{ +} + + +void OAudioInterface::init() +{ + + +} + + +/*====================================================================================== + * OMixerInterface + *======================================================================================*/ + +OMixerInterface::OMixerInterface( QObject* parent, const char* name ) + :QObject( parent, name ) +{ + qDebug( "OMixerInterface::OMixerInterface()" ); + init(); +} + + +OMixerInterface::~OMixerInterface() +{ +} + + +void OMixerInterface::init() +{ + // open the device + _fd = ::open( name(), O_RDWR ); + if ( _fd == -1 ) + { + qWarning( "can't open mixer." ); + return; + } + + // construct the device capabilities + int devmask = 0; + if ( ioctl( _fd, SOUND_MIXER_READ_DEVMASK, &devmask ) != -1 ) + { + if ( devmask & ( 1 << SOUND_MIXER_VOLUME ) ) _channels.insert( "PlayVolume", SOUND_MIXER_VOLUME ); + if ( devmask & ( 1 << SOUND_MIXER_BASS ) ) _channels.insert( "PlayBass", SOUND_MIXER_BASS ); + if ( devmask & ( 1 << SOUND_MIXER_TREBLE ) ) _channels.insert( "PlayTreble", SOUND_MIXER_TREBLE ); + if ( devmask & ( 1 << SOUND_MIXER_SYNTH ) ) _channels.insert( "PlaySynth", SOUND_MIXER_SYNTH ); + if ( devmask & ( 1 << SOUND_MIXER_PCM ) ) _channels.insert( "PlayPCM", SOUND_MIXER_PCM ); + if ( devmask & ( 1 << SOUND_MIXER_SPEAKER ) ) _channels.insert( "PlaySpeaker", SOUND_MIXER_SPEAKER ); + if ( devmask & ( 1 << SOUND_MIXER_LINE ) ) _channels.insert( "PlayLine", SOUND_MIXER_LINE ); + if ( devmask & ( 1 << SOUND_MIXER_MIC ) ) _channels.insert( "PlayMic", SOUND_MIXER_MIC ); + if ( devmask & ( 1 << SOUND_MIXER_CD ) ) _channels.insert( "PlayCD", SOUND_MIXER_CD ); + if ( devmask & ( 1 << SOUND_MIXER_IMIX ) ) _channels.insert( "PlayInputMix", SOUND_MIXER_IMIX ); + if ( devmask & ( 1 << SOUND_MIXER_ALTPCM ) ) _channels.insert( "PlayAltPCM", SOUND_MIXER_ALTPCM ); + if ( devmask & ( 1 << SOUND_MIXER_RECLEV ) ) _channels.insert( "PlayRecord", SOUND_MIXER_RECLEV ); + if ( devmask & ( 1 << SOUND_MIXER_IGAIN ) ) _channels.insert( "PlayInputGain", SOUND_MIXER_IGAIN ); + if ( devmask & ( 1 << SOUND_MIXER_OGAIN ) ) _channels.insert( "PlayOutputGain", SOUND_MIXER_OGAIN ); + //qDebug( "devmask available and constructed." ); + } + + devmask = 0; + if ( ioctl( _fd, SOUND_MIXER_READ_RECMASK, &devmask ) != -1 ) + { + if ( devmask & ( 1 << SOUND_MIXER_VOLUME ) ) _channels.insert( "RecVolume", SOUND_MIXER_VOLUME ); + if ( devmask & ( 1 << SOUND_MIXER_BASS ) ) _channels.insert( "RecBass", SOUND_MIXER_BASS ); + if ( devmask & ( 1 << SOUND_MIXER_TREBLE ) ) _channels.insert( "RecTreble", SOUND_MIXER_TREBLE ); + if ( devmask & ( 1 << SOUND_MIXER_SYNTH ) ) _channels.insert( "RecSynth", SOUND_MIXER_SYNTH ); + if ( devmask & ( 1 << SOUND_MIXER_PCM ) ) _channels.insert( "RecPCM", SOUND_MIXER_PCM ); + if ( devmask & ( 1 << SOUND_MIXER_SPEAKER ) ) _channels.insert( "RecSpeaker", SOUND_MIXER_SPEAKER ); + if ( devmask & ( 1 << SOUND_MIXER_LINE ) ) _channels.insert( "RecLine", SOUND_MIXER_LINE ); + if ( devmask & ( 1 << SOUND_MIXER_MIC ) ) _channels.insert( "RecMic", SOUND_MIXER_MIC ); + if ( devmask & ( 1 << SOUND_MIXER_CD ) ) _channels.insert( "RecCD", SOUND_MIXER_CD ); + if ( devmask & ( 1 << SOUND_MIXER_IMIX ) ) _channels.insert( "RecInputMix", SOUND_MIXER_IMIX ); + if ( devmask & ( 1 << SOUND_MIXER_ALTPCM ) ) _channels.insert( "RecAltPCM", SOUND_MIXER_ALTPCM ); + if ( devmask & ( 1 << SOUND_MIXER_RECLEV ) ) _channels.insert( "RecRecord", SOUND_MIXER_RECLEV ); + if ( devmask & ( 1 << SOUND_MIXER_IGAIN ) ) _channels.insert( "RecInputGain", SOUND_MIXER_IGAIN ); + if ( devmask & ( 1 << SOUND_MIXER_OGAIN ) ) _channels.insert( "RecOutputGain", SOUND_MIXER_OGAIN ); + //qDebug( "recmask available and constructed." ); + } + +/* ChannelIterator it; + for ( it = _channels.begin(); it != _channels.end(); ++it ) + { + qDebug( "Channel %s available (bit %d)", (const char*) it.key(), it.data() ); + qDebug( " +--- Volume: %02d | %02d", volume( it.key() ) & 0xff, volume( it.key() ) >> 8 ); + } +*/ +} + +QStringList OMixerInterface::allChannels() const +{ + ChannelIterator it = _channels.begin(); + QStringList channels; + while ( it != _channels.end() ) + { + channels += it.key(); + it++; + } + return channels; +} + + +QStringList OMixerInterface::recChannels() const +{ + qWarning( "NYI" ); +} + + +QStringList OMixerInterface::playChannels() const +{ + qWarning( "NYI" ); +} + + +bool OMixerInterface::hasChannel( const QString& channel ) +{ + return _channels.contains( channel ); +} + + +void OMixerInterface::setVolume( const QString& channel, int left, int right ) +{ + int volume = left; + volume |= ( right == -1 ) ? left << 8 : right << 8; + + if ( _channels.contains( channel ) ) + { + int result = ioctl( _fd, MIXER_WRITE( _channels[channel] ), &volume ); + if ( result == -1 ) + { + qWarning( "Can't set volume: %s", strerror( errno ) ); + } + else + { + if ( result & 0xff != left ) + { + qWarning( "Device adjusted volume from %d to %d", left, result & 0xff ); + } + } + } +} + + +int OMixerInterface::volume( const QString& channel ) const +{ + int volume; + + if ( _channels.contains( channel ) ) + { + if ( ioctl( _fd, MIXER_READ( _channels[channel] ), &volume ) == -1 ) + { + qWarning( "Can't get volume: %s", strerror( errno ) ); + } + else return volume; + } + return -1; +} + + diff --git a/libopie2/opiemm/osoundsystem.h b/libopie2/opiemm/osoundsystem.h new file mode 100644 index 0000000..096d397 --- a/dev/null +++ b/libopie2/opiemm/osoundsystem.h @@ -0,0 +1,216 @@ +/* + This file is part of the Opie Project + + (C) 2003 Michael 'Mickey' Lauer <mickey@tm.informatik.uni-frankfurt.de> + =. + .=l. + .>+-= + _;:, .> :=|. This program is free software; you can +.> <`_, > . <= redistribute it and/or modify it under +:`=1 )Y*s>-.-- : the terms of the GNU Library General Public +.="- .-=="i, .._ License as published by the Free Software + - . .-<_> .<> Foundation; either version 2 of the License, + ._= =} : or (at your option) any later version. + .%`+i> _;_. + .i_,=:_. -<s. 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 library; see the file COPYING.LIB. + If not, write to the Free Software Foundation, + Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + +*/ + +#ifndef OSOUNDSYSTEM_H +#define OSOUNDSYSTEM_H + +#include <qobject.h> +#include <qdict.h> +#include <qmap.h> + +class OAudioInterface; +class OMixerInterface; +class OSoundCard; + +/*====================================================================================== + * OSoundSystem + *======================================================================================*/ + +/** + * @brief A container class for all audio interfaces + * + * This class provides access to all available audio/midi/sequencer interfaces of your computer. + * + * @author Michael 'Mickey' Lauer <mickey@tm.informatik.uni-frankfurt.de> + */ +class OSoundSystem : public QObject +{ + Q_OBJECT + + public: + typedef QDict<OSoundCard> CardMap; + typedef QDictIterator<OSoundCard> CardIterator; + + public: + /** + * @returns the number of available interfaces + */ + int count() const; + /** + * @returns a pointer to the (one and only) @ref ONetwork instance. + */ + static OSoundSystem* instance(); + /** + * @returns an iterator usable for iterating through all network interfaces. + */ + CardIterator iterator() const; + /** + * @returns a pointer to the @ref OAudioInterface object for the specified @a interface or 0, if not found + * @see OAudioInterface + */ + OSoundCard* card( const QString& interface ) const; + /** + * @internal Rebuild the internal interface database + * @note Sometimes it might be useful to call this from client code, + * e.g. after issuing a cardctl insert + */ + void synchronize(); + + protected: + OSoundSystem(); + + private: + static OSoundSystem* _instance; + CardMap _interfaces; +}; + + +/*====================================================================================== + * OSoundCard + *======================================================================================*/ + +class OSoundCard : public QObject +{ + Q_OBJECT + + public: + /** + * Constructor. Normally you don't create @ref OSoundCard objects yourself, + * but access them via @ref OSoundSystem::card(). + */ + OSoundCard( QObject* parent, const char* name ); + /** + * Destructor. + */ + virtual ~OSoundCard(); + + bool hasMixer() const { return _audio; }; + bool hasAudio() const { return _mixer; }; + + OAudioInterface* audio() const { return _audio; }; + OMixerInterface* mixer() const { return _mixer; }; + + protected: + OAudioInterface* _audio; + OMixerInterface* _mixer; + + private: + void init(); +}; + +/*====================================================================================== + * OAudioInterface + *======================================================================================*/ + +class OAudioInterface : public QObject +{ + Q_OBJECT + + public: + /** + * Constructor. Normally you don't create @ref OAudioInterface objects yourself, + * but access them via the @ref OSoundCard interface. + */ + OAudioInterface( QObject* parent, const char* name ); + /** + * Destructor. + */ + virtual ~OAudioInterface(); + + protected: + const int _sfd; + + private: + void init(); +}; + + +/*====================================================================================== + * OMixerInterface + *======================================================================================*/ + +class OMixerInterface : public QObject +{ + Q_OBJECT + + public: + + typedef QMap<QString,int>::ConstIterator ChannelIterator; + + /** + * Constructor. Normally you don't create @ref OMixerInterface objects yourself, + * but access them via the @ref OSoundCard interface. + */ + OMixerInterface( QObject* parent, const char* name ); + /** + * Destructor. + */ + virtual ~OMixerInterface(); + + /** + * @returns all available channels. + */ + QStringList allChannels() const; + /** + * @returns recordable channels. + */ + QStringList recChannels() const; + /** + * @returns playable channels. + */ + QStringList playChannels() const; + + /** + * @returns true, if @a channel exists. + */ + bool hasChannel( const QString& channel ); + + /** + * Set the @a left and @a right volumes for @a channel. + * If no value for right is given, the value for left is taken for that. + */ + void setVolume( const QString& channel, int left, int right = -1 ); + /** + * @returns the volume of @a channel or -1, if the channel doesn't exist. + * @note You might want to use @ref hasChannel() to check if a channel exists. + */ + int volume( const QString& channel ) const; + + protected: + int _fd; + QMap<QString, int> _channels; + + private: + void init(); +}; + +#endif // OSOUNDSYSTEM_H + |