wxMidiDatabaseGM

The General MIDI (GM) Specification, published by the International MIDI Association, defines a set of general capabilities for General MIDI Instruments. The General MIDI Specification includes the definition of a General MIDI Sound Set (a patch map), a General MIDI Percussion map (mapping of percussion sounds to note numbers), and a set of General MIDI Performance capabilities (number of voices, types of MIDI messages recognized, etc.).

A MIDI sequence which has been generated for use on a General MIDI Instrument should play correctly on any General MIDI synthesizer or sound module.

The wxMidi package has a database with the General Midi standard (GM) instruments list. Instruments are grouped into sections, to facilitate the user to search for a specific instrument. The database includes methods to populate a combo box, a list box and, in general, any other control derived from wxControlWithItems.

wxMidiSystem is a singleton and, therefore, the constructor is not public. Access to the only instance must be through method GetInstance.

The General MIDI system specifies which instrument or sound corresponds with each program/patch number, but General MIDI does not specify how these sounds are produced. Thus, program number 0 should select the Acoustic Grand Piano sound on any General MIDI instrument. However, the Acoustic Grand Piano sound on two General MIDI synthesizers which use different synthesis techniques may sound quite different.

The General MIDI system utilizes MIDI channels 0-8 and 10-15 for chromatic instrument sounds, while channel number 9 is utilized for "key-based" percussion sounds.

For sounds on channels 0-8 and 10-15, the note number in a NoteOn message is used to select the pitch of the sound which will be played. For example if the Vibraphone instrument (program number 11) has been selected on channel 2, then playing note number 60 on channel 2 would play the middle C note (this would be the default note to pitch assignment on most instruments), and note number 59 on channel 2 would play B below middle C. Both notes would be played using the Vibraphone sound.

The General MIDI system specifies sounds (or instruments, in wxMidi terminilogy) by using program numbers 0 through 127. The list of all these 128 sounds could be obtained by using different methods; for example, by calling PopulateWithAllInstruments.

These instrument sounds are grouped into "sets" of related sounds. For example, instruments 0-7 are piano sounds, 8-15 are chromatic percussion sounds, 16-23 are organ sounds, 24-31 are guitar sounds, etc. Each one of these "sets" is called a "section" in the wxMidiDatabaseGM. There are two specific methods to deal with sections: GetNumSections, GetSectionName and PopulateWithSections.

The list of instruments in a section is available through method PopulateWithInstruments .

As said, channel 9 reserved for "key-based" percussion sounds. For these "key-based" sounds, the note number data in a NoteOn message is used differently. Note numbers on channel 9 are used to select which drum sound will be played. For example, a NoteOn message on channel 9 with note number 60 will play a Hi Bongo drum sound. Note number 59 on channel 9 will play the Ride Cymbal 2 sound. The list of all key-based percussion sounds is accesible trhough method PopulateWithPercusionInstr

The wxMidiDatabaseGM object includes additional methods for retrieving an instrumen name given its number or the number of the section and the index inside the section. See, for example, GetInstrFromSection, GetInstrumentName, GetNumInstrumentsInSection

 

Members

wxMidiDatabaseGM::~wxMidiDatabaseGM
wxMidiDatabaseGM::GetInstance
wxMidiDatabaseGM::GetInstrFromSection
wxMidiDatabaseGM::GetInstrumentName
wxMidiDatabaseGM::GetNumInstrumentsInSection
wxMidiDatabaseGM::GetNumSections
wxMidiDatabaseGM::GetSectionName
wxMidiDatabaseGM::PopulateWithAllInstruments
wxMidiDatabaseGM::PopulateWithInstruments
wxMidiDatabaseGM::PopulateWithPercusionInstr
wxMidiDatabaseGM::PopulateWithSections


wxMidiDatabaseGM::GetInstance

wxMidiError GetInstance()

Returns a pointer to the only wxMidiDatabaseGM instance. Note that wxMidiDatabaseGM is a singleton and, therefore, the constructor is not public. Access to the only instance must be through this GetInstance() method.


wxMidiDatabaseGM::GetInstrFromSection

int GetInstrFromSection(int nSect, int n)

Returns the GM number of the nth instrument in section nSect.

 

Parameters

nSect

n

 

Remarks

This method is useful when in your application, the instruments are presented organized into sections instead of in a single list with all GM instruments.

In the first case, when the user selects an instrument, it is necessary to translate the pair (section number, instrument number - relative to section - ) to the GM standard program number , as in following example:

// It is assumed that combo box m_pSectCombo is loaded 
// with section names and that combo box m_pInstrCombo
// is loaded with the names of the instruments
// in the selected section.

void MyFrame::OnComboInstruments(wxCommandEvent &event)
{
    // A new instrument has been selected. Change Midi program

    int nInstr = m_pInstrCombo->GetSelection();
    int nSect = m_pSectCombo->GetSelection();
    wxMidiDatabaseGM* pMidiGM = wxMidiDatabaseGM::GetInstance();
    int nProgram = pMidiGM->GetInstrFromSection(nSect, nInstr);
    int nChannel = m_channel;
    wxMidiError nErr = m_pOutDev->ProgramChange(nChannel, nProgram);
    if (nErr) {
        ...
    }
    else {
        ...
    }
}

 

See also:

GetNumInstrumentsInSection, GetNumSections, PopulateWithInstruments


wxMidiDatabaseGM::GetInstrumentName

wxString GetInstrumentName(int nInstr)

Returns a string with the name of instrumen nInstr.

 

Parameters

nInstr

 

Remarks

To populate a control (i.e. a combo box) with the names of all instruments you can do it in a single call by using method PopulateWithAllInstruments instead of doing it inside a loop of calls to GetInstrumentName().

 

See also:

PopulateWithAllInstruments, PopulateWithInstruments, PopulateWithPercusionInstr


wxMidiDatabaseGM::GetNumInstrumentsInSection

int GetNumInstrumentsInSection(int nSect)

Returns the number of instruments that are included in section number nSect. In the wxMidiDatabaseGM, the number of instruments in a section is always eight. This method was included to allow for future extensions and to deal with other MIDI standards.

Parameters

nSect

 

See also:

GetInstrFromSection, GetNumSections, GetSectionName, PopulateWithInstruments


wxMidiDatabaseGM::GetNumSections

int GetNumSections()

Returns the number of sections in which the instruments in the GM standard has been organized. In the wxMidiDatabaseGM, the number sections is always 16. This method was included to allow for future extensions and to deal with other MIDI standards.

 

See also:

GetNumInstrumentsInSection, GetSectionName, PopulateWithSections


wxMidiDatabaseGM::GetSectionName

wxString GetSectionName(int nSect)

Returns a string containig the name of section number nSect.

 

Parameters

nSect

 

Remarks

To populate a control (i.e. a combo box) with the names of all sections you can do it in a single call by using method PopulateWithSections instead of doing it inside a loop of calls to GetSectionName().

 

See also:

GetInstrFromSection, GetNumInstrumentsInSection, GetNumSections, PopulateWithSections


wxMidiDatabaseGM::PopulateWithAllInstruments

void PopulateWithAllInstruments(wxControlWithItems* pCtrol, int nInstr=0)

Load control pCtrol with the list of all instrumens in the GM standard. If nInstr is specified, the name of that instrument is left selected in the control. Otherwise, the first instrument is left selected.

Parameters

pCtrol

nInstr

 

Example:


pInstrCombo = 
    new wxComboBox(panel, ID_COMBO_INSTRUMENTS,
			_T("This"),
			wxPoint(20,25), wxSize(270, wxDefaultCoord),
			0, NULL,
			wxCB_DROPDOWN | wxCB_READONLY | wxPROCESS_ENTER);

wxMidiDatabaseGM* pMidiGM = wxMidiDatabaseGM::GetInstance();
pMidiGM->PopulateWithAllInstruments(pInstrCombo);

 

See also:

PopulateWithInstruments, PopulateWithPercusionInstr,


wxMidiDatabaseGM::PopulateWithInstruments

void PopulateWithInstruments(wxControlWithItems* pCtrol, int nSection, int nInstr=0)

Load control pCtrol with the list of all instrumens that belong to section nSection. If nInstr is specified, the name of that instrument is left selected in the control. Otherwise, the first instrument of the section is left selected.

Parameters

pCtrol

nSection

nInstr

 

Remarks:

This method is useful when in your application, the instruments are presented organized into sections instead of in a single long list with all GM instruments.

For example, you have to load a combo box with the list of all sections and other combo box with the list of instruments in currently selected section, as in following example:


MyFrame::MyFrame (...)
{
   ...

   wxMidiDatabaseGM* pMidiGM = wxMidiDatabaseGM::GetInstance();
   m_pSectCombo = 
      new wxComboBox(this, ID_COMBO_SECTIONS,
			_T("This"),
			wxPoint(20,25), wxSize(270, wxDefaultCoord),
			0, NULL,
			wxCB_DROPDOWN | wxCB_READONLY | wxPROCESS_ENTER);

   pMidiGM->PopulateWithSections(m_pSectCombo);

   m_pInstrCombo = 
      new wxComboBox(this, ID_COMBO_INSTRUMENTS,
			_T("This"),
			wxPoint(20,25), wxSize(270, wxDefaultCoord),
			0, NULL,
			wxCB_DROPDOWN | wxCB_READONLY | wxPROCESS_ENTER);

   pMidiGM->PopulateWithInstruments(m_pInstrCombo, 0, 0);

   ...
}

void MyFrame::OnComboSections(wxCommandEvent &event)
{
   // A new section selected. Reload Instruments combo
   // with the instruments in the selected section

   wxMidiDatabaseGM* pMidiGM = wxMidiDatabaseGM::GetInstance();
   int nSect = m_pSectCombo->GetSelection();
   pMidiGM->PopulateWithInstruments(m_pInstrCombo, nSect);
   DoProgramChange();

}

void MyFrame::OnComboInstruments(wxCommandEvent &event)
{
	// A new instrument selected. Change Midi program
	DoProgramChange();
}

void MyFrame::DoProgramChange()
{
    // A new instrument has been selected. Change Midi program

    int nInstr = m_pInstrCombo->GetSelection();
    int nSect = m_pSectCombo->GetSelection();
    wxMidiDatabaseGM* pMidiGM = wxMidiDatabaseGM::GetInstance();
    int nProgram = pMidiGM->GetInstrFromSection(nSect, nInstr);
    int nChannel = m_channel;
    wxMidiError nErr = m_pOutDev->ProgramChange(nChannel, nProgram);
    if (nErr) {
        ...
    }
    else {
        ...
    }

}


 

See also:

PopulateWithAllInstruments, PopulateWithPercusionInstr, PopulateWithSections


wxMidiDatabaseGM::PopulateWithPercusionInstr

void PopulateWithPercusionInstr(wxControlWithItems* pCtrol, int iSel=0)

In the MIDI standard channel 9 is reserved for "key-based" percussion sounds. For these "key-based" sounds, the note number data in a NoteOn message is used to select which drum sound will be played. For example, a NoteOn message on channel 9 with note number 60 will play a Hi Bongo drum sound. Note number 59 on channel 9 will play the Ride Cymbal 2 sound. Method PopulateWithPercusionInstr is used to load a control (combo box, list box, or other derived from wxControlWithItems) whit the list of all key-based percussion sounds in the GM standard.

Parameters

pCtrol

iSel

The list of percussion sounds in the GM standard is included here for your conveniece:

35-Acoustic Bass Drum59-Ride Cymbal 2
36-Bass Drum 160-High Bongo
37-Side Stick61-Low Bongo
38-Acoustic Snare62-Mute High Conga
39-Hand clap63-Open High Conga
40-Electric Snare64-Low Conga
41_Low Floor Tom65-High Timbale
42_Closed High-Hat66-Low Timbale
43-High Floor Tom67-High Agogo
44-Pedal High-Hat68-Low Agogo
45-Low Tom69-Casaba
46-Open High-Hat70-Maracas
47-Low-Mid Tom71-Short Whistle
48-High-Mid Tom72-Long Whistle
49-Crash Cymbal 173-Short Guiro
50-High Tom74-Long Guiro
51-Ride Cymbal 175-Claves
52-Chinese Cymbal76-High Wood Block
53-Ride Bell77-Low Wood Block
54-Tambourine78-Mute Cuica
55-Splash Cymbal79-Open Cuica
56-Cowbell80-Mute Triangle
57-Crash Cymbal 281-Open Triangle
58-Vibraslap 


wxMidiDatabaseGM::PopulateWithSections

int PopulateWithSections(wxControlWithItems* pCtrol, int nSelInstr=-1)

Load control pCtrol with the list of all sections in which the instruments in the GM standard have been organized in the wxMidiDatabaseGM. If nSelInstris specified, the name of that section is left selected in the control. Otherwise, the first section is left selected.

Parameters

pCtrol

nSelInstr

 

Remarks:

This method is useful when in your application, the instruments are presented organized into sections instead of in a single long list with all GM instruments.

See an example in PopulateWithInstruments

 

See also:

PopulateWithAllInstruments, PopulateWithPercusionInstr, PopulateWithInstruments


wxMidiDatabaseGM::~wxMidiDatabaseGM

~wxMidiDatabaseGM()

Destructor.