Skip to content
Snippets Groups Projects
Commit 4001ba01 authored by jpbl's avatar jpbl
Browse files

microphone support

parent 0e576348
No related branches found
No related tags found
No related merge requests found
Showing
with 308 additions and 17 deletions
...@@ -27,6 +27,7 @@ ...@@ -27,6 +27,7 @@
namespace SFLAudio namespace SFLAudio
{ {
class Device; class Device;
class Emitter;
class AudioLayer class AudioLayer
{ {
...@@ -54,6 +55,11 @@ namespace SFLAudio ...@@ -54,6 +55,11 @@ namespace SFLAudio
* Open the default device. * Open the default device.
*/ */
virtual Device *openDevice() = 0; virtual Device *openDevice() = 0;
/**
* Open the default capture device.
*/
virtual Emitter *openCaptureDevice() = 0;
/** /**
* Open the specified device. If the device don't * Open the specified device. If the device don't
......
...@@ -64,3 +64,6 @@ SFLAudio::Source * ...@@ -64,3 +64,6 @@ SFLAudio::Source *
SFLAudio::Emitter::getSource() SFLAudio::Emitter::getSource()
{return mSource;} {return mSource;}
bool
SFLAudio::Emitter::isNull()
{return false;}
...@@ -41,6 +41,11 @@ namespace SFLAudio ...@@ -41,6 +41,11 @@ namespace SFLAudio
void connect(Source *source); void connect(Source *source);
void connect(Context *context); void connect(Context *context);
Source *getSource(); Source *getSource();
virtual bool isNull();
virtual void play() = 0;
private: private:
Source *mSource; Source *mSource;
......
if MAINTENER_CODE if MAINTENER_CODE
noinst_PROGRAMS = example01 example02 example03 example04 noinst_PROGRAMS = example01 example02 example03 example04 example05
noinst_LTLIBRARIES = libsflaudio.la noinst_LTLIBRARIES = libsflaudio.la
libsflaudio_la_SOURCES = \ libsflaudio_la_SOURCES = \
...@@ -8,9 +8,11 @@ libsflaudio_la_SOURCES = \ ...@@ -8,9 +8,11 @@ libsflaudio_la_SOURCES = \
Context.cpp Context.hpp \ Context.cpp Context.hpp \
Device.cpp Device.hpp \ Device.cpp Device.hpp \
Emitter.cpp Emitter.hpp \ Emitter.cpp Emitter.hpp \
MicEmitter.cpp MicEmitter.hpp \
NullLayer.cpp NullLayer.hpp \ NullLayer.cpp NullLayer.hpp \
NullDevice.cpp NullDevice.hpp \
NullContext.cpp NullContext.hpp \ NullContext.cpp NullContext.hpp \
NullDevice.cpp NullDevice.hpp \
NullEmitter.hpp \
NullSource.cpp NullSource.hpp \ NullSource.cpp NullSource.hpp \
OpenALLayer.cpp OpenALLayer.hpp \ OpenALLayer.cpp OpenALLayer.hpp \
OpenALDevice.cpp OpenALDevice.hpp \ OpenALDevice.cpp OpenALDevice.hpp \
...@@ -25,13 +27,14 @@ AM_CPPFLAGS = $(PORTAUDIO_CFLAGS) -I$(top_srcdir)/libs/portaudio/pa_common -I$(t ...@@ -25,13 +27,14 @@ AM_CPPFLAGS = $(PORTAUDIO_CFLAGS) -I$(top_srcdir)/libs/portaudio/pa_common -I$(t
AM_CXXFLAGS = $(PORTAUDIO_CXXFLAGS) -I$(top_srcdir)/libs/ AM_CXXFLAGS = $(PORTAUDIO_CXXFLAGS) -I$(top_srcdir)/libs/
AM_LDFLAGS = -L$(top_srcdir)/libs/portaudio/ AM_LDFLAGS = -L$(top_srcdir)/libs/portaudio/
LIBADD = $(PORTAUDIO_LIBS) -lportaudio -lopenal LIBADD = $(PORTAUDIO_LIBS) -lportaudio -lopenal -lalut
LDADD = libsflaudio.la $(PORTAUDIO_LIBS) -lopenal -lportaudio LDADD = libsflaudio.la $(PORTAUDIO_LIBS) -lopenal -lportaudio -lalut
example01_SOURCES = example01.cpp example01_SOURCES = example01.cpp
example02_SOURCES = example02.cpp example02_SOURCES = example02.cpp
example03_SOURCES = example03.cpp example03_SOURCES = example03.cpp
example04_SOURCES = example04.cpp example04_SOURCES = example04.cpp
example05_SOURCES = example05.cpp
endif endif
/*
* Copyright (C) 2004-2005 Savoir-Faire Linux inc.
* Author: Jean-Philippe Barrette-LaPierre
* <jean-philippe.barrette-lapierre@savoirfairelinux.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU 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 General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <AL/alut.h>
#include <AL/alut.h>
#include <iostream>
#include "OpenALLayer.hpp"
#include "MicEmitter.hpp"
#include "Source.hpp"
SFLAudio::MicEmitter::MicEmitter(int format, int freq, int size,
PFNALCAPTURESTARTPROC palCaptureStart,
PFNALCAPTURESTOPPROC palCaptureStop,
PFNALCAPTUREGETDATAPROC palCaptureGetData)
: Emitter(format, freq)
, mSize(size)
, mAlCaptureStart(palCaptureStart)
, mAlCaptureStop(palCaptureStop)
, mAlCaptureGetData(palCaptureGetData)
{
mData = (ALchar *)malloc(mSize);
}
void
SFLAudio::MicEmitter::play()
{
fprintf( stderr, "recording... " );
mAlCaptureStart();
ALsizei retval = 0;
while(retval < mSize) {
void *data = &mData[retval];
ALsizei size = mSize - retval;
retval += mAlCaptureGetData(&mData[retval],
mSize - retval,
getFormat(),
getFrequency());
}
mAlCaptureStop();
std::cout << "done." << std::endl;
std::cout << "playing... ";
Source *source = getSource();
if(source && mData) {
source->play(mData, mSize);
}
std::cout << "done." << std::endl;
}
/*
* Copyright (C) 2004-2005 Savoir-Faire Linux inc.
* Author: Jean-Philippe Barrette-LaPierre
* <jean-philippe.barrette-lapierre@savoirfairelinux.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU 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 General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef __SFLAUDIO_MIC_EMITTER_HPP__
#define __SFLAUDIO_MIC_EMITTER_HPP__
#include <AL/al.h>
#include "Emitter.hpp"
namespace SFLAudio
{
class Source;
class MicEmitter : public Emitter
{
private:
MicEmitter();
public:
MicEmitter(int format, int freq, int size,
PFNALCAPTURESTARTPROC palCaptureStart,
PFNALCAPTURESTOPPROC palCaptureStop,
PFNALCAPTUREGETDATAPROC palCaptureGetData);
virtual void play();
private:
ALchar *mData;
ALsizei mSize;
PFNALCAPTURESTARTPROC mAlCaptureStart;
PFNALCAPTURESTOPPROC mAlCaptureStop;
PFNALCAPTUREGETDATAPROC mAlCaptureGetData;
};
}
#endif
/*
* Copyright (C) 2004-2005 Savoir-Faire Linux inc.
* Author: Jean-Philippe Barrette-LaPierre
* <jean-philippe.barrette-lapierre@savoirfairelinux.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU 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 General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef __SFLAUDIO_NULL_EMITTER_HPP__
#define __SFLAUDIO_NULL_EMITTER_HPP__
#include "Emitter.hpp"
namespace SFLAudio
{
class Context;
class Source;
class NullEmitter : public Emitter
{
public:
virtual bool isNull() {return true;}
virtual void play() {}
};
}
#endif
...@@ -20,6 +20,7 @@ ...@@ -20,6 +20,7 @@
#include "NullLayer.hpp" #include "NullLayer.hpp"
#include "NullDevice.hpp" #include "NullDevice.hpp"
#include "NullEmitter.hpp"
SFLAudio::NullLayer::NullLayer() SFLAudio::NullLayer::NullLayer()
: AudioLayer("NullLayer") : AudioLayer("NullLayer")
...@@ -35,6 +36,12 @@ SFLAudio::NullLayer::openDevice() ...@@ -35,6 +36,12 @@ SFLAudio::NullLayer::openDevice()
return new NullDevice(); return new NullDevice();
} }
SFLAudio::Emitter *
SFLAudio::NullLayer::openCaptureDevice()
{
return new NullEmitter();
}
SFLAudio::Device * SFLAudio::Device *
SFLAudio::NullLayer::openDevice(const std::string &) SFLAudio::NullLayer::openDevice(const std::string &)
{ {
......
...@@ -31,6 +31,7 @@ namespace SFLAudio ...@@ -31,6 +31,7 @@ namespace SFLAudio
NullLayer(); NullLayer();
std::list< std::string > getDevicesNames(); std::list< std::string > getDevicesNames();
virtual Device *openDevice(); virtual Device *openDevice();
virtual Emitter *openCaptureDevice();
virtual Device *openDevice(const std::string &name); virtual Device *openDevice(const std::string &name);
}; };
} }
......
...@@ -52,13 +52,8 @@ SFLAudio::OpenALDevice::unload() { ...@@ -52,13 +52,8 @@ SFLAudio::OpenALDevice::unload() {
bool bool
SFLAudio::OpenALDevice::load() { SFLAudio::OpenALDevice::load() {
mDevice = alcOpenDevice(0); ALCcontext *context = alcGetCurrentContext();
ALenum error = alcGetError(mDevice); mDevice = alcGetContextsDevice(context);
if (error != AL_NO_ERROR) {
std::cerr << "OpenAL::alcOpenDevice: " << alGetString(error) << std::endl;
unload();
}
if(mDevice != 0) { if(mDevice != 0) {
const ALCchar *device = alcGetString(mDevice, ALC_DEVICE_SPECIFIER); const ALCchar *device = alcGetString(mDevice, ALC_DEVICE_SPECIFIER);
setName(device); setName(device);
......
...@@ -20,18 +20,60 @@ ...@@ -20,18 +20,60 @@
#include "OpenALLayer.hpp" #include "OpenALLayer.hpp"
#include "OpenALDevice.hpp" #include "OpenALDevice.hpp"
#include "MicEmitter.hpp"
#include "NullDevice.hpp" #include "NullDevice.hpp"
#include "NullEmitter.hpp"
#include <iostream> #include <iostream>
#include <AL/al.h> #include <AL/al.h>
#include <AL/alc.h> #include <AL/alc.h>
#include <AL/alext.h>
#include <AL/alut.h>
#define DEFAULT_DEVICE_NAME "default" #define DEFAULT_DEVICE_NAME "default"
#define DEFAULT_CAPTURE_DEVICE_NAME "default" #define DEFAULT_CAPTURE_DEVICE_NAME "default"
#define FREQ 22050
#define SAMPLES (5 * FREQ)
#define SIZE (SAMPLES * 2)
#define GP(type,var,name) \
var = (type)alGetProcAddress((const ALchar*) name); \
if( var == NULL ) { \
fprintf( stderr, "Could not get %s extension entry\n", name ); \
}
SFLAudio::OpenALLayer::OpenALLayer() SFLAudio::OpenALLayer::OpenALLayer()
: AudioLayer("openal") : AudioLayer("openal")
{} {
alutInit(0, 0);
GP( PFNALCAPTUREINITPROC, palCaptureInit, "alCaptureInit_EXT" );
GP( PFNALCAPTUREDESTROYPROC, palCaptureDestroy,
"alCaptureDestroy_EXT" );
GP( PFNALCAPTURESTARTPROC, palCaptureStart, "alCaptureStart_EXT" );
GP( PFNALCAPTURESTOPPROC, palCaptureStop, "alCaptureStop_EXT" );
GP( PFNALCAPTUREGETDATAPROC, palCaptureGetData,
"alCaptureGetData_EXT" );
}
SFLAudio::Emitter *
SFLAudio::OpenALLayer::openCaptureDevice()
{
if(palCaptureInit == 0 ||
!palCaptureInit( AL_FORMAT_MONO16, FREQ, 1024 ) ) {
printf( "Unable to initialize capture\n" );
return new NullEmitter();
}
return new MicEmitter(AL_FORMAT_MONO16, FREQ, SIZE,
palCaptureStart,
palCaptureStop,
palCaptureGetData);
}
std::list< std::string > std::list< std::string >
SFLAudio::OpenALLayer::getDevicesNames() SFLAudio::OpenALLayer::getDevicesNames()
...@@ -94,7 +136,7 @@ SFLAudio::OpenALLayer::openDevice() ...@@ -94,7 +136,7 @@ SFLAudio::OpenALLayer::openDevice()
SFLAudio::Device * SFLAudio::Device *
SFLAudio::OpenALLayer::openDevice(const std::string &) SFLAudio::OpenALLayer::openDevice(const std::string &)
{ {
return new NullDevice(); return openDevice();
} }
...@@ -21,10 +21,12 @@ ...@@ -21,10 +21,12 @@
#ifndef __SFLAUDIO_OPENAL_LAYER_HPP__ #ifndef __SFLAUDIO_OPENAL_LAYER_HPP__
#define __SFLAUDIO_OPENAL_LAYER_HPP__ #define __SFLAUDIO_OPENAL_LAYER_HPP__
#include <AL/alext.h>
#include "AudioLayer.hpp" #include "AudioLayer.hpp"
namespace SFLAudio namespace SFLAudio
{ {
class OpenALLayer : public AudioLayer class OpenALLayer : public AudioLayer
{ {
public: public:
...@@ -32,8 +34,17 @@ namespace SFLAudio ...@@ -32,8 +34,17 @@ namespace SFLAudio
virtual std::list< std::string > getDevicesNames(); virtual std::list< std::string > getDevicesNames();
virtual std::list< std::string > getCaptureDevicesNames(); virtual std::list< std::string > getCaptureDevicesNames();
virtual Emitter *openCaptureDevice();
virtual Device *openDevice(); virtual Device *openDevice();
virtual Device *openDevice(const std::string &name); virtual Device *openDevice(const std::string &name);
private:
PFNALCAPTUREINITPROC palCaptureInit;
PFNALCAPTUREDESTROYPROC palCaptureDestroy;
PFNALCAPTURESTARTPROC palCaptureStart;
PFNALCAPTURESTOPPROC palCaptureStop;
PFNALCAPTUREGETDATAPROC palCaptureGetData;
}; };
} }
......
...@@ -159,7 +159,11 @@ SFLAudio::OpenALSource::create(OpenALContext *, int format, int freq) { ...@@ -159,7 +159,11 @@ SFLAudio::OpenALSource::create(OpenALContext *, int format, int freq) {
bool bool
SFLAudio::OpenALSource::isPlaying() SFLAudio::OpenALSource::isPlaying()
{ {
ALenum state; ALint state;
if(alIsSource(mSource) == AL_FALSE) {
return false;
}
alGetSourcei(mSource, AL_SOURCE_STATE, &state); alGetSourcei(mSource, AL_SOURCE_STATE, &state);
return (state == AL_PLAYING); return (state == AL_PLAYING);
......
...@@ -21,6 +21,7 @@ ...@@ -21,6 +21,7 @@
#ifndef __SFLAUDIO_OPENAL_SOURCE_HPP__ #ifndef __SFLAUDIO_OPENAL_SOURCE_HPP__
#define __SFLAUDIO_OPENAL_SOURCE_HPP__ #define __SFLAUDIO_OPENAL_SOURCE_HPP__
#include <AL/al.h>
#include <AL/alc.h> #include <AL/alc.h>
#include "Source.hpp" #include "Source.hpp"
......
...@@ -22,6 +22,7 @@ ...@@ -22,6 +22,7 @@
#include "portaudio.h" #include "portaudio.h"
#include "NullDevice.hpp" #include "NullDevice.hpp"
#include "NullEmitter.hpp"
SFLAudio::PortAudioLayer::PortAudioLayer() SFLAudio::PortAudioLayer::PortAudioLayer()
...@@ -81,6 +82,12 @@ SFLAudio::PortAudioLayer::openDevice() ...@@ -81,6 +82,12 @@ SFLAudio::PortAudioLayer::openDevice()
return new NullDevice(); return new NullDevice();
} }
SFLAudio::Emitter *
SFLAudio::PortAudioLayer::openCaptureDevice()
{
return new NullEmitter();
}
SFLAudio::Device * SFLAudio::Device *
SFLAudio::PortAudioLayer::openDevice(const std::string &) SFLAudio::PortAudioLayer::openDevice(const std::string &)
{ {
......
...@@ -35,6 +35,7 @@ namespace SFLAudio ...@@ -35,6 +35,7 @@ namespace SFLAudio
virtual std::list< std::string > getDevicesNames(); virtual std::list< std::string > getDevicesNames();
virtual Device *openDevice(); virtual Device *openDevice();
virtual Emitter *openCaptureDevice();
virtual Device *openDevice(const std::string &name); virtual Device *openDevice(const std::string &name);
private: private:
......
example01.cpp: This is an enumeration of device example. example01.cpp: This is an enumeration of device example.
example02.cpp: A simple WAV player. example02.cpp: A simple WAV player with a direct handling of sound buffer.
example03.cpp: A simple WAV player, with 2 files playing at the same time. example03.cpp: A simple WAV player, with 2 files playing at the same time.
\ No newline at end of file example04.cpp: A simple WAV player. (Uses the simple WavEmitter class)
example04.cpp: A Capture example.
...@@ -29,7 +29,6 @@ using namespace SFLAudio; ...@@ -29,7 +29,6 @@ using namespace SFLAudio;
int main(int, char* []) int main(int, char* [])
{ {
AudioLayer *layer = SFLAudio::AudioManager::instance().currentLayer(); AudioLayer *layer = SFLAudio::AudioManager::instance().currentLayer();
Device *device = layer->openDevice(); Device *device = layer->openDevice();
Context *context = device->createContext(); Context *context = device->createContext();
......
/*
* Copyright (C) 2004-2005 Savoir-Faire Linux inc.
* Author: Jean-Philippe Barrette-LaPierre
* <jean-philippe.barrette-lapierre@savoirfairelinux.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU 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 General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <iostream>
#include <list>
#include <string>
#include "SFLAudio.hpp"
#include "Emitter.hpp"
using namespace SFLAudio;
int main(int, char* [])
{
AudioLayer *layer = SFLAudio::AudioManager::instance().currentLayer();
Device *device = layer->openDevice();
Context *context = device->createContext();
Emitter *mic = layer->openCaptureDevice();
mic->connect(context);
mic->play();
// Wait for user input.
std::cout << "Press any key to quit the program." << std::endl;
std::cin.get();
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment