Commit b99fa1e4 authored by Jonas Stienen's avatar Jonas Stienen

Initial checkin

parents
cmake_minimum_required( VERSION 2.8 )
project( ITAStreaming )
list( APPEND CMAKE_MODULE_PATH "$ENV{VISTA_CMAKE_COMMON}" )
include( VistaCommon )
# dependencies
vista_use_package( ITABase REQUIRED FIND_DEPENDENCIES )
vista_use_package( ASIO )
vista_use_package( Portaudio )
if( NOT DEFINED ITA_STREAMING_WITH_BACKEND_ASIO )
set( ITA_STREAMING_WITH_BACKEND_ASIO ${VASIO_FOUND} CACHE BOOL "Build with ASIO for audio streaming" )
endif( NOT DEFINED ITA_STREAMING_WITH_BACKEND_ASIO )
if( NOT DEFINED ITA_STREAMING_WITH_BACKEND_PORTAUDIO )
set( ITA_STREAMING_WITH_BACKEND_PORTAUDIO OFF CACHE BOOL "Build with Portaudio for audio streaming" )
endif( NOT DEFINED ITA_STREAMING_WITH_BACKEND_PORTAUDIO )
if( NOT DEFINED ITA_STREAMING_WITH_BACKEND_VIRTUAL )
set( ITA_STREAMING_WITH_BACKEND_VIRTUAL ON CACHE BOOL "Build with virtual audio streaming backend" )
endif( NOT DEFINED ITA_STREAMING_WITH_BACKEND_VIRTUAL )
# includes
include_directories( "include" )
# sources
set( ITAStreamingHeader
"include/ITAStreamingBackend.h"
"include/ITAStreamingDefinitions.h"
"include/ITAStreamingComponent.h"
"include/ITAStreamingFunctionGenerator.h"
"include/ITAStreamingDevice.h"
"include/ITAStreamingProperties.h"
"include/ITAStreamingSource.h"
"include/ITAStreamingSourceRealization.h"
"include/ITAStreamingState.h"
)
set( ITAStreamingSources
"src/ITAStreamingBackend.cpp"
"src/ITAStreamingComponent.cpp"
"src/ITAStreamingFunctionGenerator.cpp"
"src/ITAStreamingProperties.cpp"
"src/ITAStreamingSource.cpp"
"src/ITAStreamingSourceRealization.cpp"
"src/ITAStreamingState.cpp"
)
if( ITA_STREAMING_WITH_BACKEND_ASIO AND VASIO_FOUND )
set( ITAStreamingSources "${ITAStreamingSources}" "src/ITAStreamingBackendASIO.h" "src/ITAStreamingBackendASIO.cpp" )
add_definitions( -DITA_STREAMING_WITH_BACKEND_ASIO -DIEEE754_64FLOAT=1 )
endif( ITA_STREAMING_WITH_BACKEND_ASIO AND VASIO_FOUND )
if( ITA_STREAMING_WITH_BACKEND_PORTAUDIO AND VPORTAUDIO_FOUND )
set( ITAStreamingSources "${ITAStreamingSources}" "src/ITAStreamingBackendPortaudio.h" "src/ITAStreamingBackendPortaudio.cpp" )
add_definitions( -DITA_STREAMING_WITH_BACKEND_PORTAUDIO )
endif( ITA_STREAMING_WITH_BACKEND_PORTAUDIO AND VPORTAUDIO_FOUND )
if( ITA_STREAMING_WITH_BACKEND_VIRTUAL )
set( ITAStreamingHeader "${ITAStreamingHeader}" "include/ITAStreamingVirtualDevice.h" )
set( ITAStreamingSources "${ITAStreamingSources}" "src/ITAStreamingVirtualDevice.cpp" )
endif( ITA_STREAMING_WITH_BACKEND_VIRTUAL )
# compiler
add_definitions( -DITA_BASE_DLL -DITA_STREAMING_DLL -DITA_STREAMING_EXPORT )
# linker
add_library( ITAStreaming SHARED ${ITAStreamingHeader} ${ITAStreamingSources} )
target_link_libraries( ITAStreaming ${VISTA_USE_PACKAGE_LIBRARIES} )
# config
vista_configure_lib( ITAStreaming )
vista_install( ITAStreaming )
set( ITASTREAMING_INCLUDE_OUTDIR "${CMAKE_CURRENT_SOURCE_DIR}/include" )
vista_create_cmake_configs( ITAStreaming )
vista_create_default_info_file( ITAStreaming )
set_property( TARGET ITAStreaming PROPERTY FOLDER "ITACoreLibs" )
# tests
set( ITASTREAMING_COMMON_BUILD TRUE )
add_subdirectory( "${CMAKE_CURRENT_SOURCE_DIR}/tests" )
/*
* ----------------------------------------------------------------
*
* ITA core libs
* (c) Copyright Institute of Technical Acoustics (ITA)
* RWTH Aachen University, Germany, 2015-2016
*
* ----------------------------------------------------------------
* ____ __________ _______
* // / //__ ___/ // _ |
* // / // / // /_| |
* // / // / // ___ |
* //__/ //__/ //__/ |__|
*
* ----------------------------------------------------------------
*
*/
#ifndef INCLUDE_WATCHER_ITA_STREAM_BACKEND
#define INCLUDE_WATCHER_ITA_STREAM_BACKEND
// ITAStreaming
#include <ITAStreamingDefinitions.h>
#include <ITAStreamingDevice.h>
// STL
#include <vector>
//! Audio backend interface
class ITA_STREAMING_API ITAStreamingBackend {
public:
static ITAStreamingBackend* GetDefaultBackend();
virtual ~ITAStreamingBackend() {};
//! Enumerates the available ASIO audio devices
// Note: Only the field sName will be set in each entry
virtual std::vector<ITAStreamingDeviceProperties> EnumerateDevices()=0;
//! Initializes an ASIO audio device for streaming
virtual ITAStreamDevice* InitializeDevice( const ITAStreamingDeviceProperties& oProps )=0;
};
#endif // INCLUDE_WATCHER_ITA_STREAM_BACKEND
/*
* ----------------------------------------------------------------
*
* ITA core libs
* (c) Copyright Institute of Technical Acoustics (ITA)
* RWTH Aachen University, Germany, 2015-2016
*
* ----------------------------------------------------------------
* ____ __________ _______
* // / //__ ___/ // _ |
* // / // / // /_| |
* // / // / // ___ |
* //__/ //__/ //__/ |__|
*
* ----------------------------------------------------------------
*
*/
#ifndef INCLUDE_WATCHER_ITA_STREAM_COMPONENT
#define INCLUDE_WATCHER_ITA_STREAM_COMPONENT
// ITA Base
#include <ITASampleFrame.h>
// ITA Streaming
#include <ITAStreamingDefinitions.h>
#include <ITAStreamingProperties.h>
#include <ITAStreamingState.h>
// STL
#include <unordered_map>
class ITAStreamingComponent;
class ITAStreamingComponentInput;
class ITAStreamingComponentOutput;
class ITAStreamingComponentInputImpl;
class ITAStreamingComponentOutputImpl;
// Schnittstelle: Nur für logische Steuerung nicht für interne Verdrahtung.
class ITA_STREAMING_API ITAStreamingComponentInput {
public:
virtual ~ITAStreamingComponentInput() {};
////! Returns the ID
//virtual int GetID() const=0;
////! Returns the parent component
//virtual ITAStreamComponent& GetStreamComponent() const=0;
//! Returns the properties of the audio stream
virtual const ITAStreamingProperties& GetStreamProperties() const=0;
//! Return if the input is connected to an output
virtual bool IsConnected() const=0;
//! Connect the input to an output
// Behavior: Error if already connected.
virtual void Connect(ITAStreamingComponentOutput&)=0;
//! Disconnect the input
// Behavior: No error if not connected.
virtual void Disconnect()=0;
};
// Schnittstelle: Nur für logische Steuerung nicht für interne Verdrahtung.
class ITA_STREAMING_API ITAStreamingComponentOutput
{
public:
virtual ~ITAStreamingComponentOutput() {};
////! Returns the ID
//virtual int GetID() const=0;
////! Returns the parent component
//virtual ITAStreamComponent& GetStreamComponent() const=0;
//! Returns the properties of the audio stream
virtual const ITAStreamingProperties& GetStreamProperties() const=0;
//! Connect the input to an output
// TODO: Ausgang darf nur einmalig beschaltet sein!
virtual void Connect(ITAStreamingComponentInput&)=0;
};
//// Interface: Stream component
//class ITAStreamComponent {
//public:
// virtual ~ITAStreamComponent() {};
//
// // --= Inputs =--
//
// //! Return the numbers of inputs
// int GetNumInputs() const;
//
// //! Access an input
// // Note: Throws an ITAException the input does not exist
// ITAStreamComponentInput& GetInput(int iID) const;
//
// // --= Outputs =--
//
// //! Return the numbers of outputs
// int GetNumOutputs() const;
//
// //! Access an output
// // Note: Throws an ITAException the output does not exist
// ITAStreamComponentOutput& GetOutput(int iID) const;
//};
//class ITAStreamComponentInputMap {
//public:
// typedef std::unordered_map<int, ITAStreamComponentInput*> Map;
// typedef Map::iterator Iterator;
// typedef Map::const_iterator ConstIterator;
//
// //! Returns the number of inputs
// int GetNumInputs() const;
//
// //! Access operators (by ID)
// // Note: Throws an ITAException if the input does not exist
// const ITAStreamComponentInput& operator[](int iID) const;
//
// ConstIterator& Begin() const;
// ConstIterator& End() const;
//
// //ITAStreamComponentInput operator[](int iID);
//};
/*
Gesamte komponente arbeitet mir gleichen Streamprops
*/
//!
class ITA_STREAMING_API ITAStreamingComponent {
public:
//! Behaviour variants
typedef enum {
PROCESS_COMPONENT=0, //!< Processing component (outputs are generated from inputs. ProcessStream is called.)
TRIGGER_COMPONENT, //!< Trigger component (no coupling between inputs an outputs. ProcessStream is not called. Manual triggering using TriggerStream).
} ITAStreamComponentMode;
typedef std::unordered_map<int, ITAStreamingComponentInput*> InputMap;
typedef std::unordered_map<int, ITAStreamingComponentOutput*> OutputMap;
//! Creates an empty components without inputs and outputs
explicit ITAStreamingComponent(const ITAStreamingProperties& oProps, ITAStreamComponentMode eMode=PROCESS_COMPONENT);
//! Returns the properties of the audio stream
// Caution: Channels is always 1 here... Refactor and improve arch...
const ITAStreamingProperties& GetStreamProperties() const;
void Reset();
// --= Inputs =--
//! Return the numbers of inputs
int GetNumInputs() const;
//! Access an input
// Note: Throws an ITAException the input does not exist
ITAStreamingComponentInput& GetInput(int iID) const;
//! Returns all inputs
//std::map<ITAStreamComponentInput&> GetInputs()
//! Adds an input and returns its ID
int AddInput(int nChannels);
//! Removes an input and returns its ID
void RemoveInput(int iID);
// --= Outputs =--
//! Return the numbers of outputs
int GetNumOutputs() const;
//! Access an output
// Note: Throws an ITAException the output does not exist
ITAStreamingComponentOutput& GetOutput(int iID) const;
//! Adds an output and returns its ID
int AddOutput(int nChannels);
//! Removes an output and returns its ID
void RemoveOutput(int iID);
//! --= Connections =--
//! Connect an input to the output of another component
//void ConnectInput(int iInputID, ITAStreamComponent* pSrc, int iSrcOutputID);
//! Disconnects an input
//void DisconnectInput(int iInputID);
//bool IsInputConnected()
//bool IsOutputConnected()
protected:
class InputDesc {
public:
int iID;
const ITASampleFrame* pBuf;
// Mögliche Zusatzfelder: bool bConnected
};
class OutputDesc {
public:
int iID;
ITASampleFrame* pBuf;
// Mögliche Zusatzfelder: bool bConnected
};
typedef std::vector<InputDesc> InputList;
typedef std::vector<OutputDesc> OutputList;
// Konstruktionsarbeit!
// TODO: Zugriffsmethoden raus und durch Struktur ersetzen.
////! Returns the buffer of an input
const ITASampleFrame& GetStreamInputBuffer(int iInputID);
////! Returns the buffer of an output
ITASampleFrame& GetStreamOutputBuffer(int iOutputID);
// Diese Paar von Funktionen besser erläutern
// This internal method requests all depending components
// on the input side to produce their next output samples
void PullInputs(const ITAStreamingState& oStreamState);
// This method is called by depending components to request
// the production of output samples on the component
void PullOutputs(const ITAStreamingState& oStreamState);
//! Hook: Process the audio samples of the stream
// Niemals selber aufrufen.
virtual void ProcessStream(const ITAStreamingComponent::InputList& vInputs,
const ITAStreamingComponent::OutputList& vOutputs,
const ITAStreamingState& oStreamState);
private:
const ITAStreamingProperties m_oStreamProps;
ITAStreamComponentMode m_eMode;
ITAStreamingState m_oStreamState; // Last stream state
ITASampleFrame m_sfSilence; // One block of zeros - used for unconnected inputs
InputMap m_pmInputs;
int m_iInputIDCounter;
OutputMap m_pmOutputs;
int m_iOutputIDCounter;
InputList m_vInputList;
OutputList m_vOutputList;
// Table: Pending components on the input-side (unique!)
typedef std::vector< std::pair<ITAStreamingComponent*, int> > ComponentTable; // (ptr, numrefs)
ComponentTable m_tInputComponents;
//! --= Connections =--
//! Connect an input to the output of another component
//void ConnectInput(int iInputID, ITAStreamComponent* pSrc, int iSrcOutputID);
void ConnectInput(ITAStreamingComponentInputImpl* pInput, ITAStreamingComponentOutputImpl* pOutput);
//! Disconnects an input
//void DisconnectInput(int iInputID);
void DisconnectInput(ITAStreamingComponentInputImpl* pInput);
friend class ITAStreamingComponentInputImpl;
};
//! Connect the output of component to the input of another component
// Note: This easy-to-use function only works if the source component has
// exactly one output and the destination component has exactly one input.
// If the components have multiple inputs or outputs you need to use
// the refined connect function (see below)
void ITA_STREAMING_API Connect(ITAStreamingComponent* pSource, ITAStreamingComponent* pDest);
//COMPONENT c;
//connect(c.inputs[0], d.outputs[1]);
//
////! Interface: Component with one input and one output
//class ITAStreamComponent11 {
//public:
//
//};
#endif // INCLUDE_WATCHER_ITA_STREAM_COMPONENT
/*
* ----------------------------------------------------------------
*
* ITA core libs
* (c) Copyright Institute of Technical Acoustics (ITA)
* RWTH Aachen University, Germany, 2015-2016
*
* ----------------------------------------------------------------
* ____ __________ _______
* // / //__ ___/ // _ |
* // / // / // /_| |
* // / // / // ___ |
* //__/ //__/ //__/ |__|
*
* ----------------------------------------------------------------
*
*/
// $Id: ITABaseDefinitions.h 2900 2012-09-17 08:42:42Z fwefers $
#ifndef INCLUDE_WATCHER_ITA_STREAMING_DEFINITIONS
#define INCLUDE_WATCHER_ITA_STREAMING_DEFINITIONS
// Import-/Export-Konventionen fr die Bibliothek definieren
#ifdef ITA_STREAMING_DLL
// Dynamische Bibliothek
#ifdef ITA_STREAMING_EXPORT
#define ITA_STREAMING_API __declspec(dllexport)
#else
#define ITA_STREAMING_API __declspec(dllimport)
#endif
#else
// Statische Bibliothek
#define ITA_STREAMING_API
#endif
#endif // INCLUDE_WATCHER_ITA_STREAMING_DEFINITIONS
/*
* ----------------------------------------------------------------
*
* ITA core libs
* (c) Copyright Institute of Technical Acoustics (ITA)
* RWTH Aachen University, Germany, 2015-2016
*
* ----------------------------------------------------------------
* ____ __________ _______
* // / //__ ___/ // _ |
* // / // / // /_| |
* // / // / // ___ |
* //__/ //__/ //__/ |__|
*
* ----------------------------------------------------------------
*
*/
#ifndef INCLUDE_WATCHER_ITA_STREAM_DEVICE
#define INCLUDE_WATCHER_ITA_STREAM_DEVICE
// ITAStreaming
#include <ITAStreamingDefinitions.h>
#include <ITAStreamingProperties.h>
// STL
#include <string>
//! Audio backend interface
class ITA_STREAMING_API ITAStreamingDeviceProperties
{
public:
std::string sName;
int iBlockSize;
double dSampleRate;
int iNumInputChannels;
int iNumOutputChannels;
ITAStreamingDeviceProperties( std::string sName, double dSampleRate, int iBlockSize, int iNumInputChannels, int iNumOutputChannels )
: sName(sName), dSampleRate(dSampleRate), iBlockSize(iBlockSize), iNumInputChannels(iNumInputChannels), iNumOutputChannels( iNumOutputChannels )
{
}
bool IsValid() const;
};
class ITAStreamDevice
{
public:
ITAStreamDevice(const ITAStreamingProperties&);
};
#endif // INCLUDE_WATCHER_ITA_STREAM_DEVICE
/*
* ----------------------------------------------------------------
*
* ITA core libs
* (c) Copyright Institute of Technical Acoustics (ITA)
* RWTH Aachen University, Germany, 2015-2016
*
* ----------------------------------------------------------------
* ____ __________ _______
* // / //__ ___/ // _ |
* // / // / // /_| |
* // / // / // ___ |
* //__/ //__/ //__/ |__|
*
* ----------------------------------------------------------------
*
*/
// $Id: $
#ifndef INCLUDE_WATCHER_ITA_STREAM_FUNCTION_GENERATOR
#define INCLUDE_WATCHER_ITA_STREAM_FUNCTION_GENERATOR
#include <ITAStreamingDefinitions.h>
#include <ITAStreamingComponent.h>
#include <atomic>
class ITA_STREAMING_API ITAStreamingFunctionGenerator : public ITAStreamingComponent
{
public:
//! Signal functions
enum
{
SINE = 0, //!< Sine signal1
TRIANGLE, //!< Triangle signal
SAWTOOTH, //!< Sawtooth signal
RECTANGLE, //!< Rectangle signal (50% duty cycle)
DIRAC, //!< Dirac impulse(s)
WHITE_NOISE //!< White noise
};
//! Constructor
/**
* Creates a new function generator with specific parameters
*
* \param oProperties Stream props
* \param iSignalFunction Signal function
* \param dFrequency Signal frequency [Hz]
* \param dAmplitude Signal amplitude
* \param bPeriodic Generate a periodic signal?
*/
ITAStreamingFunctionGenerator(const ITAStreamingProperties& oProperties,
int iSignalFunction,
double dFrequency,
float fAmplitude,
bool bPeriodic);
//! Destructor
virtual ~ITAStreamingFunctionGenerator();
//! Reset
/**
* Resets all output streams.
*/
void Reset();
//! Return the signal function
int GetFunction() const;
//! Sets the signal function
void SetFunction(int iFunction);
//! Returns the signal frequency [Hz]
double GetFrequency() const;
//! Sets the signal frequency [Hz]
void SetFrequency(double dFrequency);
//! Returns the signal period length [samples]
int GetPeriodAsSamples() const;
//! Sets the signal period length [samples]
void SetPeriodAsSamples(int iNumSamples);
//! Returns the signal period length [seconds]
double GetPeriodAsTime() const;
//! Sets the signal period length [seconds]
void SetPeriodAsTime(double dPeriodLength);
//! Return wheather periodic signal is generated
bool IsPeriodic() const;
//! Sets wheather periodic signal is generated
void SetPeriodic(bool bPeriodic);
//! Returns wheather the output is muted
bool IsMuted() const;
//! Muted/unmutes an the output
void SetMuted(bool bMuted);
//! Returns the output amplitude
float GetAmplitude() const;
//! Set the output gain
void SetAmplitude(float fAmplitude);
private:
std::atomic< int > m_iFunction;
std::atomic< bool > m_bPeriodic;
std::atomic< bool > m_bMuted;
std::atomic< int > m_iNumSamples;
std::atomic< float > m_fAmplitude;
std::atomic< int > m_iPeriodLengthSamples; //!< Number of samples per period
float m_fPhase; //!< Current phase information [radiants]
int m_iSampleCount; //!< Number of generated output samples
// Generate the output samples
void ProcessStream(const ITAStreamingComponent::InputList& vInputs,
const ITAStreamingComponent::OutputList& vOutputs,
const ITAStreamingState& oStreamState);
};
#endif // INCLUDE_WATCHER_ITA_STREAM_FUNCTION_GENERATOR
/*
* ----------------------------------------------------------------
*
* ITA core libs
* (c) Copyright Institute of Technical Acoustics (ITA)
* RWTH Aachen University, Germany, 2015-2016
*
* ----------------------------------------------------------------
* ____ __________ _______
* // / //__ ___/ // _ |
* // / // / // /_| |
* // / // / // ___ |
* //__/ //__/ //__/ |__|
*
* ----------------------------------------------------------------
*
*/
#ifndef INCLUDE_WATCHER_ITA_STREAM_PROPERTIES
#define INCLUDE_WATCHER_ITA_STREAM_PROPERTIES
#include <ITAStreamingDefinitions.h>
//! Properties of an audio stream
class ITA_STREAMING_API ITAStreamingProperties
{
public:
double dSampleRate; //!< Audio sampling rate [Hertz]
int iNumChannels; //!< Number of channels
int iBlockLength; //!< Audio streaming block length (buffer size, frame size) [Samples]
ITAStreamingProperties();
explicit ITAStreamingProperties( double dSampleRate, int iNumChannels, int iBlockLength );
virtual ~ITAStreamingProperties();
//! Comparison operator
/**
* A comparison results in a true statement, if the properties sample rate, channel number and block length are equal.
*/
bool operator==( const ITAStreamingProperties& rhs ) const;
bool operator!=( const ITAStreamingProperties& rhs ) const;
//! Validity check
/**
* A valid stream has a sample rate and block size greater zero and at least a single channel.
*/
bool IsValid() const;
};
#endif // INCLUDE_WATCHER_ITA_STREAM_PROPERTIES
/*
* ----------------------------------------------------------------
*
* ITA core libs
* (c) Copyright Institute of Technical Acoustics (ITA)
* RWTH Aachen University, Germany, 2015-2016
*
* ----------------------------------------------------------------
* ____ __________ _______
* // / //__ ___/ // _ |
* // / // / // /_| |
* // / // / // ___ |
* //__/ //__/ //__/ |__|
*
* ----------------------------------------------------------------
*
*/
// $Id: ITAStreamSource.h,v 1.7 2008-12-12 12:52:43 fwefers Exp $
#ifndef INCLUDE_WATCHER_ITA_STREAMDATASOURCE
#define INCLUDE_WATCHER_ITA_STREAMDATASOURCE
#include <ITAStreamingDefinitions.h>
#include <ITAStreamingProperties.h>
#include <ITAStreamingState.h>
#include <ITASampleFrame.h>
//#include <ITAAtomicPrimitives.h>
class ITA_STREAMING_API ITAStreamingSource
{
public:
//! Destruktor
virtual ~ITAStreamingSource() {}
//! Returns the properties of the audio stream
virtual const ITAStreamingProperties& GetStreamProperties() const=0;
//! Returns the data (samples) of a specific channel of the audio stream
// DOKU:
//! Blockzeiger abrufen
/**
* Diese Methode gibt den Zeiger auf das float-Array zurück,
* in dem der nächsten Block Daten gespeichert ist. Solch ein
* Zeiger wird auch Blockzeiger genannt.
*
* \param uiChannel Index des Kanals (Wertebereich: [0, Kanäle-1])
* \param pStreamInfo Zustandsinformationen des Streams (niemals nullptr)
*
* \return Zeiger auf das float-Array mit den nächsten Daten
* des angegebenen Kanals