Chris@559: /**********************************************************************/ Chris@559: /*! \class RtMidi Chris@559: \brief An abstract base class for realtime MIDI input/output. Chris@559: Chris@559: This class implements some common functionality for the realtime Chris@559: MIDI input/output subclasses RtMidiIn and RtMidiOut. Chris@559: Chris@559: RtMidi WWW site: http://music.mcgill.ca/~gary/rtmidi/ Chris@559: Chris@559: RtMidi: realtime MIDI i/o C++ classes Chris@1397: Copyright (c) 2003-2016 Gary P. Scavone Chris@559: Chris@559: Permission is hereby granted, free of charge, to any person Chris@559: obtaining a copy of this software and associated documentation files Chris@559: (the "Software"), to deal in the Software without restriction, Chris@559: including without limitation the rights to use, copy, modify, merge, Chris@559: publish, distribute, sublicense, and/or sell copies of the Software, Chris@559: and to permit persons to whom the Software is furnished to do so, Chris@559: subject to the following conditions: Chris@559: Chris@559: The above copyright notice and this permission notice shall be Chris@559: included in all copies or substantial portions of the Software. Chris@559: Chris@559: Any person wishing to distribute modifications to the Software is Chris@1397: asked to send the modifications to the original developer so that Chris@1397: they can be incorporated into the canonical version. This is, Chris@1397: however, not a binding provision of this license. Chris@559: Chris@559: THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, Chris@559: EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF Chris@559: MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. Chris@559: IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR Chris@559: ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF Chris@559: CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION Chris@559: WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. Chris@559: */ Chris@559: /**********************************************************************/ Chris@559: Chris@1397: /*! Chris@1397: \file RtMidi.h Chris@1397: */ Chris@559: Chris@559: #ifndef RTMIDI_H Chris@559: #define RTMIDI_H Chris@559: Chris@1397: #define RTMIDI_VERSION "2.1.1" Chris@1397: Chris@1397: #include Chris@1397: #include Chris@559: #include Chris@1397: #include Chris@1397: Chris@1397: /************************************************************************/ Chris@1397: /*! \class RtMidiError Chris@1397: \brief Exception handling class for RtMidi. Chris@1397: Chris@1397: The RtMidiError class is quite simple but it does allow errors to be Chris@1397: "caught" by RtMidiError::Type. See the RtMidi documentation to know Chris@1397: which methods can throw an RtMidiError. Chris@1397: */ Chris@1397: /************************************************************************/ Chris@1397: Chris@1397: class RtMidiError : public std::exception Chris@1397: { Chris@1397: public: Chris@1397: //! Defined RtMidiError types. Chris@1397: enum Type { Chris@1397: WARNING, /*!< A non-critical error. */ Chris@1397: DEBUG_WARNING, /*!< A non-critical error which might be useful for debugging. */ Chris@1397: UNSPECIFIED, /*!< The default, unspecified error type. */ Chris@1397: NO_DEVICES_FOUND, /*!< No devices found on system. */ Chris@1397: INVALID_DEVICE, /*!< An invalid device ID was specified. */ Chris@1397: MEMORY_ERROR, /*!< An error occured during memory allocation. */ Chris@1397: INVALID_PARAMETER, /*!< An invalid parameter was specified to a function. */ Chris@1397: INVALID_USE, /*!< The function was called incorrectly. */ Chris@1397: DRIVER_ERROR, /*!< A system driver error occured. */ Chris@1397: SYSTEM_ERROR, /*!< A system error occured. */ Chris@1397: THREAD_ERROR /*!< A thread error occured. */ Chris@1397: }; Chris@1397: Chris@1397: //! The constructor. Chris@1397: RtMidiError( const std::string& message, Type type = RtMidiError::UNSPECIFIED ) throw() : message_(message), type_(type) {} Chris@1397: Chris@1397: //! The destructor. Chris@1397: virtual ~RtMidiError( void ) throw() {} Chris@1397: Chris@1397: //! Prints thrown error message to stderr. Chris@1397: virtual void printMessage( void ) const throw() { std::cerr << '\n' << message_ << "\n\n"; } Chris@1397: Chris@1397: //! Returns the thrown error message type. Chris@1397: virtual const Type& getType(void) const throw() { return type_; } Chris@1397: Chris@1397: //! Returns the thrown error message string. Chris@1397: virtual const std::string& getMessage(void) const throw() { return message_; } Chris@1397: Chris@1397: //! Returns the thrown error message as a c-style string. Chris@1397: virtual const char* what( void ) const throw() { return message_.c_str(); } Chris@1397: Chris@1397: protected: Chris@1397: std::string message_; Chris@1397: Type type_; Chris@1397: }; Chris@1397: Chris@1397: //! RtMidi error callback function prototype. Chris@1397: /*! Chris@1397: \param type Type of error. Chris@1397: \param errorText Error description. Chris@1397: Chris@1397: Note that class behaviour is undefined after a critical error (not Chris@1397: a warning) is reported. Chris@1397: */ Chris@1397: typedef void (*RtMidiErrorCallback)( RtMidiError::Type type, const std::string &errorText, void *userData ); Chris@1397: Chris@1397: class MidiApi; Chris@559: Chris@559: class RtMidi Chris@559: { Chris@559: public: Chris@559: Chris@1397: //! MIDI API specifier arguments. Chris@1397: enum Api { Chris@1397: UNSPECIFIED, /*!< Search for a working compiled API. */ Chris@1397: MACOSX_CORE, /*!< Macintosh OS-X Core Midi API. */ Chris@1397: LINUX_ALSA, /*!< The Advanced Linux Sound Architecture API. */ Chris@1397: UNIX_JACK, /*!< The JACK Low-Latency MIDI Server API. */ Chris@1397: WINDOWS_MM, /*!< The Microsoft Multimedia MIDI API. */ Chris@1397: RTMIDI_DUMMY /*!< A compilable but non-functional API. */ Chris@1397: }; Chris@1397: Chris@1397: //! A static function to determine the current RtMidi version. Chris@1397: static std::string getVersion( void ) throw(); Chris@1397: Chris@1397: //! A static function to determine the available compiled MIDI APIs. Chris@1397: /*! Chris@1397: The values returned in the std::vector can be compared against Chris@1397: the enumerated list values. Note that there can be more than one Chris@1397: API compiled for certain operating systems. Chris@1397: */ Chris@1397: static void getCompiledApi( std::vector &apis ) throw(); Chris@1397: Chris@559: //! Pure virtual openPort() function. Chris@565: virtual void openPort( unsigned int portNumber = 0, const std::string portName = std::string( "RtMidi" ) ) = 0; Chris@559: Chris@559: //! Pure virtual openVirtualPort() function. Chris@559: virtual void openVirtualPort( const std::string portName = std::string( "RtMidi" ) ) = 0; Chris@559: Chris@559: //! Pure virtual getPortCount() function. Chris@559: virtual unsigned int getPortCount() = 0; Chris@559: Chris@559: //! Pure virtual getPortName() function. Chris@559: virtual std::string getPortName( unsigned int portNumber = 0 ) = 0; Chris@559: Chris@559: //! Pure virtual closePort() function. Chris@559: virtual void closePort( void ) = 0; Chris@559: Chris@1397: //! Returns true if a port is open and false if not. Chris@1397: virtual bool isPortOpen( void ) const = 0; Chris@1397: Chris@1397: //! Set an error callback function to be invoked when an error has occured. Chris@1397: /*! Chris@1397: The callback function will be called whenever an error has occured. It is best Chris@1397: to set the error callback function before opening a port. Chris@1397: */ Chris@1397: virtual void setErrorCallback( RtMidiErrorCallback errorCallback = NULL, void *userData = 0 ) = 0; Chris@1397: Chris@559: protected: Chris@559: Chris@559: RtMidi(); Chris@1397: virtual ~RtMidi(); Chris@559: Chris@1397: MidiApi *rtapi_; Chris@559: }; Chris@559: Chris@559: /**********************************************************************/ Chris@559: /*! \class RtMidiIn Chris@559: \brief A realtime MIDI input class. Chris@559: Chris@559: This class provides a common, platform-independent API for Chris@559: realtime MIDI input. It allows access to a single MIDI input Chris@559: port. Incoming MIDI messages are either saved to a queue for Chris@559: retrieval using the getMessage() function or immediately passed to Chris@559: a user-specified callback function. Create multiple instances of Chris@559: this class to connect to more than one MIDI device at the same Chris@1397: time. With the OS-X, Linux ALSA, and JACK MIDI APIs, it is also Chris@1397: possible to open a virtual input port to which other MIDI software Chris@1397: clients can connect. Chris@559: Chris@1397: by Gary P. Scavone, 2003-2014. Chris@559: */ Chris@559: /**********************************************************************/ Chris@559: Chris@1397: // **************************************************************** // Chris@1397: // Chris@1397: // RtMidiIn and RtMidiOut class declarations. Chris@1397: // Chris@1397: // RtMidiIn / RtMidiOut are "controllers" used to select an available Chris@1397: // MIDI input or output interface. They present common APIs for the Chris@1397: // user to call but all functionality is implemented by the classes Chris@1397: // MidiInApi, MidiOutApi and their subclasses. RtMidiIn and RtMidiOut Chris@1397: // each create an instance of a MidiInApi or MidiOutApi subclass based Chris@1397: // on the user's API choice. If no choice is made, they attempt to Chris@1397: // make a "logical" API selection. Chris@1397: // Chris@1397: // **************************************************************** // Chris@559: Chris@559: class RtMidiIn : public RtMidi Chris@559: { Chris@559: public: Chris@559: Chris@559: //! User callback function type definition. Chris@559: typedef void (*RtMidiCallback)( double timeStamp, std::vector *message, void *userData); Chris@559: Chris@1397: //! Default constructor that allows an optional api, client name and queue size. Chris@559: /*! Chris@1397: An exception will be thrown if a MIDI system initialization Chris@1397: error occurs. The queue size defines the maximum number of Chris@1397: messages that can be held in the MIDI queue (when not using a Chris@1397: callback function). If the queue size limit is reached, Chris@1397: incoming messages will be ignored. Chris@1397: Chris@1397: If no API argument is specified and multiple API support has been Chris@1397: compiled, the default order of use is ALSA, JACK (Linux) and CORE, Chris@1397: JACK (OS-X). Chris@1397: Chris@1397: \param api An optional API id can be specified. Chris@1397: \param clientName An optional client name can be specified. This Chris@1397: will be used to group the ports that are created Chris@1397: by the application. Chris@1397: \param queueSizeLimit An optional size of the MIDI input queue can be specified. Chris@559: */ Chris@1397: RtMidiIn( RtMidi::Api api=UNSPECIFIED, Chris@1397: const std::string clientName = std::string( "RtMidi Input Client"), Chris@1397: unsigned int queueSizeLimit = 100 ); Chris@559: Chris@559: //! If a MIDI connection is still open, it will be closed by the destructor. Chris@1397: ~RtMidiIn ( void ) throw(); Chris@559: Chris@1397: //! Returns the MIDI API specifier for the current instance of RtMidiIn. Chris@1397: RtMidi::Api getCurrentApi( void ) throw(); Chris@1397: Chris@1397: //! Open a MIDI input connection given by enumeration number. Chris@559: /*! Chris@1397: \param portNumber An optional port number greater than 0 can be specified. Chris@1397: Otherwise, the default or first port found is opened. Chris@1397: \param portName An optional name for the application port that is used to connect to portId can be specified. Chris@559: */ Chris@1397: void openPort( unsigned int portNumber = 0, const std::string portName = std::string( "RtMidi Input" ) ); Chris@559: Chris@1397: //! Create a virtual input port, with optional name, to allow software connections (OS X, JACK and ALSA only). Chris@559: /*! Chris@1397: This function creates a virtual MIDI input port to which other Chris@1397: software applications can connect. This type of functionality Chris@1397: is currently only supported by the Macintosh OS-X, any JACK, Chris@1397: and Linux ALSA APIs (the function returns an error for the other APIs). Chris@1397: Chris@1397: \param portName An optional name for the application port that is Chris@1397: used to connect to portId can be specified. Chris@559: */ Chris@559: void openVirtualPort( const std::string portName = std::string( "RtMidi Input" ) ); Chris@559: Chris@559: //! Set a callback function to be invoked for incoming MIDI messages. Chris@559: /*! Chris@1397: The callback function will be called whenever an incoming MIDI Chris@1397: message is received. While not absolutely necessary, it is best Chris@1397: to set the callback function before opening a MIDI port to avoid Chris@1397: leaving some messages in the queue. Chris@1397: Chris@1397: \param callback A callback function must be given. Chris@1397: \param userData Optionally, a pointer to additional data can be Chris@1397: passed to the callback function whenever it is called. Chris@559: */ Chris@559: void setCallback( RtMidiCallback callback, void *userData = 0 ); Chris@559: Chris@559: //! Cancel use of the current callback function (if one exists). Chris@559: /*! Chris@1397: Subsequent incoming MIDI messages will be written to the queue Chris@1397: and can be retrieved with the \e getMessage function. Chris@559: */ Chris@559: void cancelCallback(); Chris@559: Chris@559: //! Close an open MIDI connection (if one exists). Chris@559: void closePort( void ); Chris@559: Chris@1397: //! Returns true if a port is open and false if not. Chris@1397: virtual bool isPortOpen() const; Chris@1397: Chris@559: //! Return the number of available MIDI input ports. Chris@1397: /*! Chris@1397: \return This function returns the number of MIDI ports of the selected API. Chris@1397: */ Chris@559: unsigned int getPortCount(); Chris@559: Chris@559: //! Return a string identifier for the specified MIDI input port number. Chris@559: /*! Chris@1397: \return The name of the port with the given Id is returned. Chris@1397: \retval An empty string is returned if an invalid port specifier is provided. Chris@559: */ Chris@559: std::string getPortName( unsigned int portNumber = 0 ); Chris@559: Chris@559: //! Specify whether certain MIDI message types should be queued or ignored during input. Chris@559: /*! Chris@1397: By default, MIDI timing and active sensing messages are ignored Chris@1397: during message input because of their relative high data rates. Chris@1397: MIDI sysex messages are ignored by default as well. Variable Chris@1397: values of "true" imply that the respective message type will be Chris@1397: ignored. Chris@559: */ Chris@559: void ignoreTypes( bool midiSysex = true, bool midiTime = true, bool midiSense = true ); Chris@559: Chris@559: //! Fill the user-provided vector with the data bytes for the next available MIDI message in the input queue and return the event delta-time in seconds. Chris@559: /*! Chris@1397: This function returns immediately whether a new message is Chris@1397: available or not. A valid message is indicated by a non-zero Chris@1397: vector size. An exception is thrown if an error occurs during Chris@1397: message retrieval or an input connection was not previously Chris@1397: established. Chris@559: */ Chris@559: double getMessage( std::vector *message ); Chris@559: Chris@1397: //! Set an error callback function to be invoked when an error has occured. Chris@1397: /*! Chris@1397: The callback function will be called whenever an error has occured. It is best Chris@1397: to set the error callback function before opening a port. Chris@1397: */ Chris@1397: virtual void setErrorCallback( RtMidiErrorCallback errorCallback = NULL, void *userData = 0 ); Chris@559: Chris@1397: protected: Chris@1397: void openMidiApi( RtMidi::Api api, const std::string clientName, unsigned int queueSizeLimit ); Chris@559: Chris@559: }; Chris@559: Chris@559: /**********************************************************************/ Chris@559: /*! \class RtMidiOut Chris@559: \brief A realtime MIDI output class. Chris@559: Chris@559: This class provides a common, platform-independent API for MIDI Chris@559: output. It allows one to probe available MIDI output ports, to Chris@559: connect to one such port, and to send MIDI bytes immediately over Chris@559: the connection. Create multiple instances of this class to Chris@1397: connect to more than one MIDI device at the same time. With the Chris@1397: OS-X, Linux ALSA and JACK MIDI APIs, it is also possible to open a Chris@1397: virtual port to which other MIDI software clients can connect. Chris@559: Chris@1397: by Gary P. Scavone, 2003-2014. Chris@559: */ Chris@559: /**********************************************************************/ Chris@559: Chris@559: class RtMidiOut : public RtMidi Chris@559: { Chris@559: public: Chris@559: Chris@565: //! Default constructor that allows an optional client name. Chris@559: /*! Chris@1397: An exception will be thrown if a MIDI system initialization error occurs. Chris@1397: Chris@1397: If no API argument is specified and multiple API support has been Chris@1397: compiled, the default order of use is ALSA, JACK (Linux) and CORE, Chris@1397: JACK (OS-X). Chris@559: */ Chris@1397: RtMidiOut( RtMidi::Api api=UNSPECIFIED, Chris@1397: const std::string clientName = std::string( "RtMidi Output Client") ); Chris@559: Chris@559: //! The destructor closes any open MIDI connections. Chris@1397: ~RtMidiOut( void ) throw(); Chris@1397: Chris@1397: //! Returns the MIDI API specifier for the current instance of RtMidiOut. Chris@1397: RtMidi::Api getCurrentApi( void ) throw(); Chris@559: Chris@559: //! Open a MIDI output connection. Chris@559: /*! Chris@559: An optional port number greater than 0 can be specified. Chris@559: Otherwise, the default or first port found is opened. An Chris@559: exception is thrown if an error occurs while attempting to make Chris@559: the port connection. Chris@559: */ Chris@565: void openPort( unsigned int portNumber = 0, const std::string portName = std::string( "RtMidi Output" ) ); Chris@559: Chris@559: //! Close an open MIDI connection (if one exists). Chris@1397: void closePort( void ); Chris@559: Chris@1397: //! Returns true if a port is open and false if not. Chris@1397: virtual bool isPortOpen() const; Chris@1397: Chris@1397: //! Create a virtual output port, with optional name, to allow software connections (OS X, JACK and ALSA only). Chris@559: /*! Chris@559: This function creates a virtual MIDI output port to which other Chris@559: software applications can connect. This type of functionality Chris@1397: is currently only supported by the Macintosh OS-X, Linux ALSA Chris@1397: and JACK APIs (the function does nothing with the other APIs). Chris@1397: An exception is thrown if an error occurs while attempting to Chris@1397: create the virtual port. Chris@559: */ Chris@559: void openVirtualPort( const std::string portName = std::string( "RtMidi Output" ) ); Chris@559: Chris@559: //! Return the number of available MIDI output ports. Chris@1397: unsigned int getPortCount( void ); Chris@559: Chris@559: //! Return a string identifier for the specified MIDI port type and number. Chris@559: /*! Chris@1397: An empty string is returned if an invalid port specifier is provided. Chris@559: */ Chris@559: std::string getPortName( unsigned int portNumber = 0 ); Chris@559: Chris@559: //! Immediately send a single message out an open MIDI output port. Chris@559: /*! Chris@559: An exception is thrown if an error occurs during output or an Chris@559: output connection was not previously established. Chris@559: */ Chris@559: void sendMessage( std::vector *message ); Chris@559: Chris@1397: //! Set an error callback function to be invoked when an error has occured. Chris@1397: /*! Chris@1397: The callback function will be called whenever an error has occured. It is best Chris@1397: to set the error callback function before opening a port. Chris@1397: */ Chris@1397: virtual void setErrorCallback( RtMidiErrorCallback errorCallback = NULL, void *userData = 0 ); Chris@559: Chris@1397: protected: Chris@1397: void openMidiApi( RtMidi::Api api, const std::string clientName ); Chris@1397: }; Chris@1397: Chris@1397: Chris@1397: // **************************************************************** // Chris@1397: // Chris@1397: // MidiInApi / MidiOutApi class declarations. Chris@1397: // Chris@1397: // Subclasses of MidiInApi and MidiOutApi contain all API- and Chris@1397: // OS-specific code necessary to fully implement the RtMidi API. Chris@1397: // Chris@1397: // Note that MidiInApi and MidiOutApi are abstract base classes and Chris@1397: // cannot be explicitly instantiated. RtMidiIn and RtMidiOut will Chris@1397: // create instances of a MidiInApi or MidiOutApi subclass. Chris@1397: // Chris@1397: // **************************************************************** // Chris@1397: Chris@1397: class MidiApi Chris@1397: { Chris@1397: public: Chris@1397: Chris@1397: MidiApi(); Chris@1397: virtual ~MidiApi(); Chris@1397: virtual RtMidi::Api getCurrentApi( void ) = 0; Chris@1397: virtual void openPort( unsigned int portNumber, const std::string portName ) = 0; Chris@1397: virtual void openVirtualPort( const std::string portName ) = 0; Chris@1397: virtual void closePort( void ) = 0; Chris@1397: Chris@1397: virtual unsigned int getPortCount( void ) = 0; Chris@1397: virtual std::string getPortName( unsigned int portNumber ) = 0; Chris@1397: Chris@1397: inline bool isPortOpen() const { return connected_; } Chris@1397: void setErrorCallback( RtMidiErrorCallback errorCallback, void *userData ); Chris@1397: Chris@1397: //! A basic error reporting function for RtMidi classes. Chris@1397: void error( RtMidiError::Type type, std::string errorString ); Chris@1397: Chris@1397: protected: Chris@1397: virtual void initialize( const std::string& clientName ) = 0; Chris@1397: Chris@1397: void *apiData_; Chris@1397: bool connected_; Chris@1397: std::string errorString_; Chris@1397: RtMidiErrorCallback errorCallback_; Chris@1397: bool firstErrorOccurred_; Chris@1397: void *errorCallbackUserData_; Chris@1397: }; Chris@1397: Chris@1397: class MidiInApi : public MidiApi Chris@1397: { Chris@1397: public: Chris@1397: Chris@1397: MidiInApi( unsigned int queueSizeLimit ); Chris@1397: virtual ~MidiInApi( void ); Chris@1397: void setCallback( RtMidiIn::RtMidiCallback callback, void *userData ); Chris@1397: void cancelCallback( void ); Chris@1397: virtual void ignoreTypes( bool midiSysex, bool midiTime, bool midiSense ); Chris@1397: double getMessage( std::vector *message ); Chris@1397: Chris@1397: // A MIDI structure used internally by the class to store incoming Chris@1397: // messages. Each message represents one and only one MIDI message. Chris@1397: struct MidiMessage { Chris@1397: std::vector bytes; Chris@1397: double timeStamp; Chris@1397: Chris@1397: // Default constructor. Chris@1397: MidiMessage() Chris@1397: :bytes(0), timeStamp(0.0) {} Chris@1397: }; Chris@1397: Chris@1397: struct MidiQueue { Chris@1397: unsigned int front; Chris@1397: unsigned int back; Chris@1397: unsigned int size; Chris@1397: unsigned int ringSize; Chris@1397: MidiMessage *ring; Chris@1397: Chris@1397: // Default constructor. Chris@1397: MidiQueue() Chris@1397: :front(0), back(0), size(0), ringSize(0) {} Chris@1397: }; Chris@1397: Chris@1397: // The RtMidiInData structure is used to pass private class data to Chris@1397: // the MIDI input handling function or thread. Chris@1397: struct RtMidiInData { Chris@1397: MidiQueue queue; Chris@1397: MidiMessage message; Chris@1397: unsigned char ignoreFlags; Chris@1397: bool doInput; Chris@1397: bool firstMessage; Chris@1397: void *apiData; Chris@1397: bool usingCallback; Chris@1397: RtMidiIn::RtMidiCallback userCallback; Chris@1397: void *userData; Chris@1397: bool continueSysex; Chris@1397: Chris@1397: // Default constructor. Chris@1397: RtMidiInData() Chris@1397: : ignoreFlags(7), doInput(false), firstMessage(true), Chris@1397: apiData(0), usingCallback(false), userCallback(0), userData(0), Chris@1397: continueSysex(false) {} Chris@1397: }; Chris@1397: Chris@1397: protected: Chris@1397: RtMidiInData inputData_; Chris@1397: }; Chris@1397: Chris@1397: class MidiOutApi : public MidiApi Chris@1397: { Chris@1397: public: Chris@1397: Chris@1397: MidiOutApi( void ); Chris@1397: virtual ~MidiOutApi( void ); Chris@1397: virtual void sendMessage( std::vector *message ) = 0; Chris@1397: }; Chris@1397: Chris@1397: // **************************************************************** // Chris@1397: // Chris@1397: // Inline RtMidiIn and RtMidiOut definitions. Chris@1397: // Chris@1397: // **************************************************************** // Chris@1397: Chris@1397: inline RtMidi::Api RtMidiIn :: getCurrentApi( void ) throw() { return rtapi_->getCurrentApi(); } Chris@1397: inline void RtMidiIn :: openPort( unsigned int portNumber, const std::string portName ) { rtapi_->openPort( portNumber, portName ); } Chris@1397: inline void RtMidiIn :: openVirtualPort( const std::string portName ) { rtapi_->openVirtualPort( portName ); } Chris@1397: inline void RtMidiIn :: closePort( void ) { rtapi_->closePort(); } Chris@1397: inline bool RtMidiIn :: isPortOpen() const { return rtapi_->isPortOpen(); } Chris@1397: inline void RtMidiIn :: setCallback( RtMidiCallback callback, void *userData ) { ((MidiInApi *)rtapi_)->setCallback( callback, userData ); } Chris@1397: inline void RtMidiIn :: cancelCallback( void ) { ((MidiInApi *)rtapi_)->cancelCallback(); } Chris@1397: inline unsigned int RtMidiIn :: getPortCount( void ) { return rtapi_->getPortCount(); } Chris@1397: inline std::string RtMidiIn :: getPortName( unsigned int portNumber ) { return rtapi_->getPortName( portNumber ); } Chris@1397: inline void RtMidiIn :: ignoreTypes( bool midiSysex, bool midiTime, bool midiSense ) { ((MidiInApi *)rtapi_)->ignoreTypes( midiSysex, midiTime, midiSense ); } Chris@1397: inline double RtMidiIn :: getMessage( std::vector *message ) { return ((MidiInApi *)rtapi_)->getMessage( message ); } Chris@1397: inline void RtMidiIn :: setErrorCallback( RtMidiErrorCallback errorCallback, void *userData ) { rtapi_->setErrorCallback(errorCallback, userData); } Chris@1397: Chris@1397: inline RtMidi::Api RtMidiOut :: getCurrentApi( void ) throw() { return rtapi_->getCurrentApi(); } Chris@1397: inline void RtMidiOut :: openPort( unsigned int portNumber, const std::string portName ) { rtapi_->openPort( portNumber, portName ); } Chris@1397: inline void RtMidiOut :: openVirtualPort( const std::string portName ) { rtapi_->openVirtualPort( portName ); } Chris@1397: inline void RtMidiOut :: closePort( void ) { rtapi_->closePort(); } Chris@1397: inline bool RtMidiOut :: isPortOpen() const { return rtapi_->isPortOpen(); } Chris@1397: inline unsigned int RtMidiOut :: getPortCount( void ) { return rtapi_->getPortCount(); } Chris@1397: inline std::string RtMidiOut :: getPortName( unsigned int portNumber ) { return rtapi_->getPortName( portNumber ); } Chris@1397: inline void RtMidiOut :: sendMessage( std::vector *message ) { ((MidiOutApi *)rtapi_)->sendMessage( message ); } Chris@1397: inline void RtMidiOut :: setErrorCallback( RtMidiErrorCallback errorCallback, void *userData ) { rtapi_->setErrorCallback(errorCallback, userData); } Chris@1397: Chris@1397: // **************************************************************** // Chris@1397: // Chris@1397: // MidiInApi and MidiOutApi subclass prototypes. Chris@1397: // Chris@1397: // **************************************************************** // Chris@1397: Chris@1397: #if !defined(__LINUX_ALSA__) && !defined(__UNIX_JACK__) && !defined(__MACOSX_CORE__) && !defined(__WINDOWS_MM__) Chris@1397: #define __RTMIDI_DUMMY__ Chris@1397: #endif Chris@1397: Chris@1397: #if defined(__MACOSX_CORE__) Chris@1397: Chris@1397: class MidiInCore: public MidiInApi Chris@1397: { Chris@1397: public: Chris@1397: MidiInCore( const std::string clientName, unsigned int queueSizeLimit ); Chris@1397: ~MidiInCore( void ); Chris@1397: RtMidi::Api getCurrentApi( void ) { return RtMidi::MACOSX_CORE; }; Chris@1397: void openPort( unsigned int portNumber, const std::string portName ); Chris@1397: void openVirtualPort( const std::string portName ); Chris@1397: void closePort( void ); Chris@1397: unsigned int getPortCount( void ); Chris@1397: std::string getPortName( unsigned int portNumber ); Chris@1397: Chris@1397: protected: Chris@1397: void initialize( const std::string& clientName ); Chris@1397: }; Chris@1397: Chris@1397: class MidiOutCore: public MidiOutApi Chris@1397: { Chris@1397: public: Chris@1397: MidiOutCore( const std::string clientName ); Chris@1397: ~MidiOutCore( void ); Chris@1397: RtMidi::Api getCurrentApi( void ) { return RtMidi::MACOSX_CORE; }; Chris@1397: void openPort( unsigned int portNumber, const std::string portName ); Chris@1397: void openVirtualPort( const std::string portName ); Chris@1397: void closePort( void ); Chris@1397: unsigned int getPortCount( void ); Chris@1397: std::string getPortName( unsigned int portNumber ); Chris@1397: void sendMessage( std::vector *message ); Chris@1397: Chris@1397: protected: Chris@565: void initialize( const std::string& clientName ); Chris@559: }; Chris@559: Chris@559: #endif Chris@1397: Chris@1397: #if defined(__UNIX_JACK__) Chris@1397: Chris@1397: class MidiInJack: public MidiInApi Chris@1397: { Chris@1397: public: Chris@1397: MidiInJack( const std::string clientName, unsigned int queueSizeLimit ); Chris@1397: ~MidiInJack( void ); Chris@1397: RtMidi::Api getCurrentApi( void ) { return RtMidi::UNIX_JACK; }; Chris@1397: void openPort( unsigned int portNumber, const std::string portName ); Chris@1397: void openVirtualPort( const std::string portName ); Chris@1397: void closePort( void ); Chris@1397: unsigned int getPortCount( void ); Chris@1397: std::string getPortName( unsigned int portNumber ); Chris@1397: Chris@1397: protected: Chris@1397: std::string clientName; Chris@1397: Chris@1397: void connect( void ); Chris@1397: void initialize( const std::string& clientName ); Chris@1397: }; Chris@1397: Chris@1397: class MidiOutJack: public MidiOutApi Chris@1397: { Chris@1397: public: Chris@1397: MidiOutJack( const std::string clientName ); Chris@1397: ~MidiOutJack( void ); Chris@1397: RtMidi::Api getCurrentApi( void ) { return RtMidi::UNIX_JACK; }; Chris@1397: void openPort( unsigned int portNumber, const std::string portName ); Chris@1397: void openVirtualPort( const std::string portName ); Chris@1397: void closePort( void ); Chris@1397: unsigned int getPortCount( void ); Chris@1397: std::string getPortName( unsigned int portNumber ); Chris@1397: void sendMessage( std::vector *message ); Chris@1397: Chris@1397: protected: Chris@1397: std::string clientName; Chris@1397: Chris@1397: void connect( void ); Chris@1397: void initialize( const std::string& clientName ); Chris@1397: }; Chris@1397: Chris@1397: #endif Chris@1397: Chris@1397: #if defined(__LINUX_ALSA__) Chris@1397: Chris@1397: class MidiInAlsa: public MidiInApi Chris@1397: { Chris@1397: public: Chris@1397: MidiInAlsa( const std::string clientName, unsigned int queueSizeLimit ); Chris@1397: ~MidiInAlsa( void ); Chris@1397: RtMidi::Api getCurrentApi( void ) { return RtMidi::LINUX_ALSA; }; Chris@1397: void openPort( unsigned int portNumber, const std::string portName ); Chris@1397: void openVirtualPort( const std::string portName ); Chris@1397: void closePort( void ); Chris@1397: unsigned int getPortCount( void ); Chris@1397: std::string getPortName( unsigned int portNumber ); Chris@1397: Chris@1397: protected: Chris@1397: void initialize( const std::string& clientName ); Chris@1397: }; Chris@1397: Chris@1397: class MidiOutAlsa: public MidiOutApi Chris@1397: { Chris@1397: public: Chris@1397: MidiOutAlsa( const std::string clientName ); Chris@1397: ~MidiOutAlsa( void ); Chris@1397: RtMidi::Api getCurrentApi( void ) { return RtMidi::LINUX_ALSA; }; Chris@1397: void openPort( unsigned int portNumber, const std::string portName ); Chris@1397: void openVirtualPort( const std::string portName ); Chris@1397: void closePort( void ); Chris@1397: unsigned int getPortCount( void ); Chris@1397: std::string getPortName( unsigned int portNumber ); Chris@1397: void sendMessage( std::vector *message ); Chris@1397: Chris@1397: protected: Chris@1397: void initialize( const std::string& clientName ); Chris@1397: }; Chris@1397: Chris@1397: #endif Chris@1397: Chris@1397: #if defined(__WINDOWS_MM__) Chris@1397: Chris@1397: class MidiInWinMM: public MidiInApi Chris@1397: { Chris@1397: public: Chris@1397: MidiInWinMM( const std::string clientName, unsigned int queueSizeLimit ); Chris@1397: ~MidiInWinMM( void ); Chris@1397: RtMidi::Api getCurrentApi( void ) { return RtMidi::WINDOWS_MM; }; Chris@1397: void openPort( unsigned int portNumber, const std::string portName ); Chris@1397: void openVirtualPort( const std::string portName ); Chris@1397: void closePort( void ); Chris@1397: unsigned int getPortCount( void ); Chris@1397: std::string getPortName( unsigned int portNumber ); Chris@1397: Chris@1397: protected: Chris@1397: void initialize( const std::string& clientName ); Chris@1397: }; Chris@1397: Chris@1397: class MidiOutWinMM: public MidiOutApi Chris@1397: { Chris@1397: public: Chris@1397: MidiOutWinMM( const std::string clientName ); Chris@1397: ~MidiOutWinMM( void ); Chris@1397: RtMidi::Api getCurrentApi( void ) { return RtMidi::WINDOWS_MM; }; Chris@1397: void openPort( unsigned int portNumber, const std::string portName ); Chris@1397: void openVirtualPort( const std::string portName ); Chris@1397: void closePort( void ); Chris@1397: unsigned int getPortCount( void ); Chris@1397: std::string getPortName( unsigned int portNumber ); Chris@1397: void sendMessage( std::vector *message ); Chris@1397: Chris@1397: protected: Chris@1397: void initialize( const std::string& clientName ); Chris@1397: }; Chris@1397: Chris@1397: #endif Chris@1397: Chris@1397: #if defined(__RTMIDI_DUMMY__) Chris@1397: Chris@1397: class MidiInDummy: public MidiInApi Chris@1397: { Chris@1397: public: Chris@1397: MidiInDummy( const std::string /*clientName*/, unsigned int queueSizeLimit ) : MidiInApi( queueSizeLimit ) { errorString_ = "MidiInDummy: This class provides no functionality."; error( RtMidiError::WARNING, errorString_ ); } Chris@1397: RtMidi::Api getCurrentApi( void ) { return RtMidi::RTMIDI_DUMMY; } Chris@1397: void openPort( unsigned int /*portNumber*/, const std::string /*portName*/ ) {} Chris@1397: void openVirtualPort( const std::string /*portName*/ ) {} Chris@1397: void closePort( void ) {} Chris@1397: unsigned int getPortCount( void ) { return 0; } Chris@1399: std::string getPortName( unsigned int /*portNumber*/ ) { return ""; } Chris@1397: Chris@1397: protected: Chris@1397: void initialize( const std::string& /*clientName*/ ) {} Chris@1397: }; Chris@1397: Chris@1397: class MidiOutDummy: public MidiOutApi Chris@1397: { Chris@1397: public: Chris@1397: MidiOutDummy( const std::string /*clientName*/ ) { errorString_ = "MidiOutDummy: This class provides no functionality."; error( RtMidiError::WARNING, errorString_ ); } Chris@1397: RtMidi::Api getCurrentApi( void ) { return RtMidi::RTMIDI_DUMMY; } Chris@1397: void openPort( unsigned int /*portNumber*/, const std::string /*portName*/ ) {} Chris@1397: void openVirtualPort( const std::string /*portName*/ ) {} Chris@1397: void closePort( void ) {} Chris@1397: unsigned int getPortCount( void ) { return 0; } Chris@1397: std::string getPortName( unsigned int /*portNumber*/ ) { return ""; } Chris@1397: void sendMessage( std::vector * /*message*/ ) {} Chris@1397: Chris@1397: protected: Chris@1397: void initialize( const std::string& /*clientName*/ ) {} Chris@1397: }; Chris@1397: Chris@1397: #endif Chris@1397: Chris@1397: #endif