1
//---------------------------------------------------------------------------------------
2
// LenMus Phonascus: The teacher of music
3
// Copyright (c) 2002-2012 LenMus project
5
// This program is free software; you can redistribute it and/or modify it under the
6
// terms of the GNU General Public License as published by the Free Software Foundation,
7
// either version 3 of the License, or (at your option) any later version.
9
// This program is distributed in the hope that it will be useful, but WITHOUT ANY
10
// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
11
// PARTICULAR PURPOSE. See the GNU General Public License for more details.
13
// You should have received a copy of the GNU General Public License along with this
14
// program. If not, see <http://www.gnu.org/licenses/>.
16
// For any comment, suggestion or feature request, please contact the manager of
17
// the project at cecilios@users.sourceforge.net
19
//---------------------------------------------------------------------------------------
21
//#ifndef __LENMUS_THEOHARMONYTOOLSET_H__ //to avoid nested includes
22
//#define __LENMUS_THEOHARMONYTOOLSET_H__
24
//#if defined(__GNUG__) && !defined(NO_GCC_PRAGMA)
25
//#pragma interface "Harmony.cpp"
28
//#include "lenmus_standard_header.h"
30
//#include "../auxmusic/Chord.h"
33
//// Chord harmony types and classes
37
//// GLOBAL AUX FUNCTIONS
45
//// -1: negative, 0, 1: positive
46
//extern int GetHarmonicDirection(int nInterval);
47
//extern void DrawArrow(ImoNote* pNote1, ImoNote* pNote2, wxColour color);
48
////returns interval number ignoring octaves: 1=unison, 2=2nd, ..., 8=8ve
49
//extern int GetIntervalNumberFromFPitchDistance(FPitch n2, FPitch n1);
50
//extern void SortChordNotes( int numNotes, ImoNote** inpChordNotes);
51
//extern void SortChordNotes(int nNumNotes, FPitch fInpChordNotes[]);
52
//extern FIntval FPitchInterval(int nRootStep, EKeySignature nKey, int nIncrementSteps);
53
//// todo: move this to "Pitch" file o merge this with FPitch_ToAbsLDPName
54
//// This is just FPitch_ToAbsLDPName but WITHOUT OCTAVE
55
//extern wxString NormalizedFPitch_ToAbsLDPName(FPitch fp);
56
//extern wxString GetChordDegreeString(StepType nStep);
57
//extern wxString Get4VoiceName(int nVoice);
62
//enum lmHarmonicMovementType {
63
// lm_eDirectMovement , // 2 voices with the same delta sign (cero included)
64
// lm_eObliqueMovement , // one delta sign is 0, the other not
65
// lm_eContraryMovement // 2 voices with contrary delta sign (cero not included)
67
//extern int GetHarmonicMovementType( FPitch fVoice10, FPitch fVoice11, FPitch fVoice20, FPitch fVoice21);
70
////--------------------------------------------------------------------------
72
//// with individual absolute end time
73
//// with global absolute current time
74
////--------------------------------------------------------------------------
75
//typedef struct lmActiveNoteInfoStruct {
78
// lmActiveNoteInfoStruct(ImoNote* pNoteS, float rEndTimeS)
81
// rEndTime = rEndTimeS;
91
// void SetTime(float rNewCurrentTime);
92
// inline float GetTime() { return m_rCurrentTime; };
93
// int GetNotes(ImoNote** pNotes);
94
// void AddNote(ImoNote* pNote, float rEndTime);
95
// void RecalculateActiveNotes();
96
// int GetNumActiveNotes();
99
// wxString ToString();
102
// void ResetNotes();
104
// float m_rCurrentTime;
105
// std::list<lmActiveNoteInfo*> m_ActiveNotesInfo;
109
//// To store all the possible errors resulting from chord analysis
110
//// Error <--> broken rule
111
//// Basically it is a compressed list of rule identifiers. Each rule is a bit
112
//typedef struct lmChordErrorStruct
114
// unsigned int nErrList;
115
// bool IncludesError(int nBrokenRule); // arg: lmChordValidationRules
116
// void SetError(int nBrokenRule, bool fVal); // arg1: lmChordValidationRules
120
//#define lmMAX_NUM_CHORDS 50
123
//// lmFPitchChord is a Chord with notes in FPitch
124
//// lmScoreChord is a Chord with notes in FPitch and in ImoNote
126
//// we implement a very simple RTTI (run-time type information)
128
//// lmScoreChord inherits from lmFPitchChord
130
//// lmRule::Evaluate must be able to work with chord descriptors of both kinds
131
//// lmScoreChord: when the results draw thing areound the notes (message box, arrows, etc)
132
//// lmFPitchChord: whne the results do not draw anything; just want to know the result of the rule over the chord
134
//// lmScoreChord must be the type used to access notes from lmRule::Evaluate
138
//// Chord is an "abstract" chord: defined by intervals.
139
//// Chord: Number of notes = number of intervals +1
140
//// lmFPitchChord is a "real" chord: it contains a set of actual notes in FPitch
141
//// lmNChord: Number of notes can be ANY; IT ALLOWS DUPLICATED NOTES.
142
//// lmScoreChord: lmFPitchChord with notes of in ImoNote
143
//// TODO: move this class to Chord.cpp?
144
//class lmFPitchChord: public Chord
147
// // Constructors from notes
148
// // (the notes can not be added afterwards)
149
// //build a chord from a list of ordered notes
150
// lmFPitchChord(int nNumNotes, FPitch fNotes[], EKeySignature nKey = k_key_C);
151
// lmFPitchChord(int nNumNotes, ImoNote** pNotes, EKeySignature nKey = k_key_C);
152
// // Constructors without notes
153
// // (the notes can be added afterwards)
154
// // build a chord from "essential" information
155
// lmFPitchChord(int nDegree, EKeySignature nKey, int nNumIntervals, int nNumInversions, int octave);
157
// /* TODO: possibly helpful // Creates a chord from an unordered list of ordered score notes
158
// lmFPitchChord(EKeySignature nKey, lmActiveNotes* pActiveNotesList); --*/
160
// virtual ~lmFPitchChord(){};
162
// int get_num_notes() {return m_nNumChordNotes;}
164
// wxString ToString();
166
// FPitch GetNoteFpitch(int nIndex) {return m_fpChordNotes[nIndex];} ;
167
// // GetVoice should not be used for this class since it has no lmNotes (just FPitch)
168
// // but just in case, it can be emulated, since the notes are ordered
169
// // note 0 -> voice 4
170
// //.. note 3 -> voice 1
171
// int GetNoteVoice(int nNoteIndex)
173
// assert(nNoteIndex<m_nNumChordNotes);
174
// return m_nNumChordNotes-nNoteIndex;
177
// // aware: to be used only after using constructor without notes
178
// // return the number of notes
179
// int AddNoteLmFPitch(FPitch fNote);
181
// void RemoveAllNotes(); // todo: not necessary, remove?
183
// bool IsBassDuplicated();
184
// // todo: consider to implement: int CreateRandomNotes(int nNumNotes);
187
// int m_nNumChordNotes;
188
// FPitch m_fpChordNotes[k_notes_in_chord];
189
// bool m_fCreatedWithNotes;
192
//class lmScoreChord: public lmFPitchChord
195
// //build a chord from a list of score note pointers
196
// lmScoreChord(int nNumNotes, ImoNote** pNotes, EKeySignature nKey = k_key_C);
197
// // Constructors without notes
198
// // (the notes can be added afterwards)
199
// // build a chord from "essential" information
200
// lmScoreChord(int nDegree, EKeySignature nKey, int nNumIntervals, int nNumInversions, int octave);
202
// virtual ~lmScoreChord() {}; // TODO: review virtual destructors (needed if ancestors destructors must be called)
204
// void RemoveAllNotes(); // todo: no necessary. Remove?
206
// bool HasLmNotes() {return m_nNumLmNotes > 0 && m_nNumLmNotes == m_nNumChordNotes;}
208
// // aware: this is only to associate the score note (ImoNote) to a note in FPitch that already exists
209
// // it is not to add a note!
210
// bool SetLmNote(ImoNote* pNote);
212
// ImoNote* GetNoteLmNote(int nIndex);
213
// int GetNoteVoice(int nIndex);
214
// int GetNumLmNotes();
215
// wxString ToString();
217
// lmChordError tChordErrors;
219
// int m_nNumLmNotes;
221
// ImoNote* m_pChordNotes[k_notes_in_chord];
229
//// Message box to display the results if the chord analysis
233
//// x: relative to object; positive: right
234
//// y: relative to top line; positive: down
238
// ChordInfoBox(wxSize* pSize, lmFontInfo* pFontInfo
239
// , int nBoxX, int nBoxY, int nLineX, int nLineY, int nBoxYIncrement);
240
// ~ChordInfoBox() {};
242
// void Settings(wxSize* pSize, lmFontInfo* pFontInfo
243
// , int nBoxX, int nBoxY, int nLineX, int nLineY, int nBoxYIncrement);
244
// void DisplayChordInfo(lmScore* pScore, lmScoreChord* pChordDsct, wxColour colour, wxString &sText);
245
// void ResetPosition();
246
// void SetYPosition(int nYpos);
251
// int m_ntConstBoxXstart;
252
// int m_ntConstLineXstart;
253
// int m_ntConstLineYStart;
255
// // Variable values: only Box Y position: incremented in each use
256
// int m_ntConstInitialBoxYStart;
257
// int m_ntConstBoxYIncrement;
258
// int m_ntCurrentBoxYStart;
260
// lmFontInfo* m_pFontInfo;
269
//enum lmChordValidationRules
271
// lmCVR_ChordHasAllSteps, // The chord is complete (has all note steps)
272
// lmCVR_FirstChordValidationRule = lmCVR_ChordHasAllSteps,
273
// lmCVR_ChordHasAllNotes, // lm_eFifthMissing - Acorde completo. Contiene todas las notas (en todo caso, elidir la 5ª)
274
// lmCVR_NoParallelMotion, // No parallel motion of perfect octaves, perfect fifths, and unisons
275
// lmCVR_NoResultingFifthOctaves,
276
// // lm_eResultantFifthOctves - No hacer 5ªs ni 8ªs resultantes, excepto:
277
// //> a) la soprano se ha movido por segundas
278
// //> b) (para 5ªs) uno de los sonidos ya estaba
279
// lmCVR_NoFifthDoubled, // The fifth is not doubled
280
// lmCVR_NoLeadingToneDoubled, // The leading tone is never doubled
281
// lmCVR_LeadingToneResolveToTonic, // Scale degree seven (the leading tone) should resolve to tonic.
282
// lmCVR_SeventhResolution, // m_eSeventhResolution - the seventh of a chord should always resolve down by second.
283
// lmCVR_NoIntervalHigherThanOctave, // voices interval not greater than one octave (except bass-tenor)
284
// lmCVR_NoVoicesCrossing, // Do not allow voices crossing. No duplicates
285
// lmCVR_NoVoicesOverlap, // Voice overlap: when a voice moves above or below a pitch previously sounded by another voice.
286
// lmCVR_ChromaticAlterationsDirection, // Resolve chromatic alterations by step in the same direction than the alteration.
287
// lmCVR_NoIntervalHigherThanSixth, // lm_eGreaterThanSixth - No es conveniente exceder el intervalo de sexta, exceptuando la octava justa
288
// lmCVR_BassMovementByStep, // If bass moves by step all other voices moves in opposite direction to bass
289
// lmCVR_ThirdDoubledInBrokenCadence, // lm_eNotDoubledThird - Cuando el bajo enlaza el V grado con el VI (cadencia rota), en el acorde de VI grado se duplica la tercera.
290
// lmCVR_LastChordValidationRule = lmCVR_ThirdDoubledInBrokenCadence,
296
//// Base virtual class of rules
301
// /// DECLARE_ABSTRACT_CLASS(lmRule) //@@ TODO: aclarar ¿necesario?
303
// lmRule(int nRuleID);
304
// virtual ~lmRule(){};
305
// virtual int Evaluate(wxString& sResultDetails, int pNumFailuresInChord[], ChordInfoBox* pBox )=0;
306
// void SetChordDescriptor(lmScoreChord** pChD, int nNumChords)
308
// m_pChordDescriptor = pChD;
309
// m_nNumChords = nNumChords;
311
// bool IsEnabled(){ return m_fEnabled; };
312
// void Enable( bool fVal ){ m_fEnabled = fVal; };
313
// wxString GetDescription() { return m_sDescription;};
314
// void SetDescription(const wxString& sDescription) { m_sDescription = sDescription;};
315
// int GetRuleId() { return m_nRuleId;};
318
// lmScoreChord** m_pChordDescriptor; // array of chord pointers
320
// wxString m_sDescription;
321
// wxString m_sDetails;
326
//// The list of rules
328
//// possibly useful: typedef std::map<int, lmRule*> lmRuleMapType;
332
// lmRuleList(lmScoreChord** pChD, int nNumChords);
335
// bool AddRule(lmRule* pNewRule, const wxString& sDescription ); // return: ok
336
// bool DeleteRule(int nRuleId); // arg: lmChordValidationRules; return: ok
337
// lmRule* GetRule(int nRuleId); // arg: lmChordValidationRules;
338
// void SetChordDescriptor(lmScoreChord** pChD, int nNumChords);
341
// void CreateRules();
342
// std::map<int, lmRule*> m_Rules;
347
//// Derived classes of rules
349
//// TODO: improve this with a template...
350
//// Aware: text describing the rule must be set dynamically, since it
351
//// hast to be translated and therefore it requieres _("") instead of the static _T("")
352
//#define LM_CREATE_CHORD_RULE(classname, id) \
353
//class classname : public lmRule \
356
// classname() :lmRule(id) {}; \
357
// int Evaluate(wxString& sResultDetails, int pNumFailuresInChord[], ChordInfoBox* pBox); \
361
//// GLOBAL AUX FUNCTIONS
364
//extern void HDisplayChordInfo(lmScore* pScore, lmScoreChord* pChordDsct
365
// , wxColour colour, wxString &sText, bool reset);
366
//// Analyze a progress (link) errors in a sequence o chords
367
//extern int AnalyzeHarmonicProgression(lmScoreChord** pChordDescriptor, int nNCH, ChordInfoBox* pChordErrorBox = 0);
370
//} //namespace lenmus