MIDI-Perl Music Page
This page and the perl scripts described below are a work in progress. The scripts have been written for my own use but are also to some extent a development in support of, and a spin-off from, a research project looking at basic harmonic structures in music: 'Modulating Oscillatory Systems' and 'Reflection' described in other pages on this website.
The scripts are made available 'as is', without warranty or support (though with heavy commenting for programmers and this guide for the general user), are of decidedly 'alpha' status and the work of an amateur. Though written for use with the MIDI output from the original Acorn/RISC OS version of the music editor Sibelius, the scripts should be usable with most standard MIDI files. There are also scripts dealing with numbers and sorting at the end of this page.
Basically the approach is to convert the music data into textual form and manipulate or examine this textual description of a composition using the Perl scripts below. Facilities are also provided to re-convert the altered text data back into MIDI format so as to be able to load it into a music editor or sequencer. While the earlier AWK scripts (now withdrawn) focused on analysis, the Perl scripts as well as containing analytical features, also provide for a degree of synthesis.
Initially, the mid2txt
perl script was written in 2003 to provide a platform independent method of producing a textual description of a piece of music - via the MIDI format (Musical Instrument Digital Interface). However, later, version 0.02 of mid2txt
also functions as the 'doorway' to a set of perl scripts that manipulate mid2txt
's text-list output to achieve a number of further ends. Below is an inventory of the scripts and initial aims of this project.
mid2txt
- converts a MIDI file into a textual description in score-list format (note starttime + duration) or event-list format (note_on and note_off events).txt2mos
- creates structures of nested harmonic series (modulating oscillatory systems - MOS) based on the chord progressions of a composition.newH1
- amends the (edited) output of txt2mos to take account of changes introduced by an analyst (i.e. to the positions of the middle level nested series).mos2col
- converts the (edited) output from txt2mos into conveniently formatted columns for entry into a MOS analysis (see EX_S2.PDF).txt2inv
- outputs (in score list format) an 'harmonic reflection' of a composition by strict inversion.txt2ret
- outputs (in score list format) a composition in strict retrograde form.txt2txt
- checks text lists, converts a score list to an event list and vice versa; converts type 1 score lists to type 0 and converts both type 1 and 0 score lists to an harmonic summary expressed in midi note numbers.txtconcat
- concatenates MIDI files track by track. (Written by David C.)txt2mid
converts the text list output of the above scripts back into a MIDI file, which can be loaded into a music editor or sequencer.baseN, digseq, divisor, tacker
-- scripts concerned with numbers and digits.
The scripts depend on the powerful functions of the MIDI-perl modules (which require Perl 5.001 or above) written by Sean Burke - freely available from CPAN. Indeed, the above scripts do little more than press buttons (hopefully the right ones) in the right order; handing over the tricky work to the modules. I would like to record my thanks to Sean for making these modules available.
(For a powerful MIDI-to-chord-symbols perl script which also uses the MIDI-Perl modules, see midi2chord by Markus Kollmar.)
Perl Scripts
Introduction
Weaving a path through the scripts, with the different switches, inputs and outputs can be confusing at times, so there is a map below. Essentially, the scripts manipulate music data in textual form; but first the music data originating from a music editor or sequencer in MIDI format, must be converted to text; and perhaps at the end of a process re-converted back to MIDI data. The conversion from, and re-conversion to, MIDI file is handled by the scripts mid2txt
and txt2mid
- they are the gate-keepers. Between the entry from, and the exit to MIDI format, the remaining scripts offer a number of features for the manipulation of text files (lists) describing musical compositions.
Score-list or Event-list
It is probably helpful to keep in mind that there are two text list formats: Score-lists and Event-lists. Score lists contain information in the form of note-starttime (tick offset from beginning) plus note-duration (in ticks), which is somewhat more musician friendly than event list information in a time-chain of tick offsets from previous events -i.e. note_on and note_off events used by MIDI devices. Ticks or tick division is the basic MIDI unit of time for the user, most often set at 96 pulses (ticks) per quarternote - 96ppqn.
Map of Perl Scripts
input-MIDI-file
|
mid2txt
default | -e switch
Score-list<------------------------------>Event-list
| |
------------------------------- <--txt2txt--> m2t2t_awk
| | | | | |
| txtconcat txt2inv txt2ret txt2mos->(newH1)->mos2col AWKscripts->
| | | | |
| --------------------------> <----- |
| default | -e switch |
canon txt2mid |
| |
output-MIDI-file MOS/MBN analysis
At present the principle functions offered by the scripts are:
- The generation of a textual description of a composition -
mid2txt
- The creation of MOS (modulating oscillatory system) format text files - sequences of interlocking harmonic series - from the chord progressions within a piece of music -
txt2mos
- The rotation (strict inversion) of the harmony of a piece of music about a given axis or note. This produces similar, but not identical results to the mirror compositions (Contrapunctus 12 & 13) from Art of Fugue by J.S.Bach -
txt2inv
- Creation of the retrograde sequence of a composition -
txt2ret
- The concatenation of MIDI files -
txtconcat
- The conversion of a textual description of a composition back into MIDI format -
txt2mid
- The reduction of a composition to an harmonic image expressed in MIDI note numbers at a given granularity -
txt2txt -cs2c
- Scanning for potential canons in a given harmonic sequence -
canon
- The production of text lists for the analytical AWK scripts.
mid2txt
Converts a MIDI file into textual description in either score list (default) or event list format.
Usage: [perl] mid2txt [-e -h] input-MIDI-file
- -e change default score list output to event list output.
- -h print help/usage message.
Output is to STDOUT, which can be redirected to file, for example:
mid2txt -e input-MIDI-file > output-text-file
would send an event list to the output file specified. By default a score list is produced (note starttime + duration) this can be changed to an event list of note_on and note_off commands with the -e switch.
Note: mid2txt
and the scripts generally, are quite sensitive to inconsistent input data like excess or missing note_on/note_offs - while there are no doubt weaknesses in the code of these perl scripts themselves, if difficulties arise, the first thing to check is the quality of the input data.
Here is an exerpt from a mid2txt
output file: the first bar from J.S.Bach's setting of the chorale 'Ach Gott und Herr', in score list format.
MIDI file output in plain text:
MThd (6 bytes)
Format 1 (2 tracks)
Metrical time (TickDiv = 96 ppqn)
Track: 0
@notes = ( # 2 notes...
['key_signature', 0, 0, 0],
['time_signature', 0, 4, 2, 24, 8],
['set_tempo', 72, 1000000],
);
Track: 1
@notes = ( # 152 notes...
['control_change', 288, 0, 0, 0],
['control_change', 288, 0, 32, 0],
['patch_change', 288, 0, 0],
['control_change', 288, 0, 10, 64],
['control_change', 288, 0, 91, 61],
['note', 288, 96, 0, 67, 74],
['note', 288, 96, 0, 72, 78],
['note', 288, 96, 0, 48, 76],
['note', 288, 96, 0, 64, 78],
['note', 384, 96, 0, 67, 75],
['note', 384, 96, 0, 71, 75],
['note', 384, 96, 0, 55, 78],
['note', 384, 96, 0, 62, 78],
['note', 480, 96, 0, 66, 69],
['note', 480, 96, 0, 69, 67],
['note', 480, 48, 0, 50, 76],
['note', 480, 48, 0, 62, 78],
['note', 528, 48, 0, 50, 69],
['note', 528, 48, 0, 60, 72],
['note', 576, 96, 0, 62, 64],
['note', 576, 96, 0, 67, 68],
['note', 576, 96, 0, 43, 63],
['note', 576, 96, 0, 59, 70],
['note', 672, 48, 0, 64, 68],
['note', 672, 48, 0, 67, 75],
['note', 672, 48, 0, 48, 80],
['note', 672, 48, 0, 60, 78],
['note', 720, 48, 0, 62, 69],
['note', 720, 48, 0, 67, 73],
['note', 720, 48, 0, 48, 72],
['note', 720, 48, 0, 58, 68],
['note', 768, 96, 0, 60, 82],
['note', 768, 96, 0, 69, 87],
['note', 768, 48, 0, 53, 74],
['note', 768, 48, 0, 57, 74],
etc...
);
txt2mos
Usage: [perl] txt2mos [-a<n> -b<n> -h -d<n> -k<n> -m<n> -o -r -s<n> -w<n>] mid2txt_score_list [> myfile]
NOTE This script requires access to the database files:
- mosmbn.dir
- mosmbn.pag
Examples
- -a288 adjustment in ticks from start of measure zero to pick-up note, default 0
- -b0 first bar/measure number, default 1
- -d120 tick division, default 96
- -k7 specify fundamental key/tonal center period (H1), default first/highest
- -m288 measure length in ticks when no time-sig in MIDI data, default 384
- -r restrict display of redundant slices, default display all slices
- -o print overview of chords and conjunctions at end of file
- -s turn off automatic smoothing of nested and aggregated series, default on
- -w96 slice width in ticks, default 48
Taking the switches in order:
The -a switch is used to tell the txt2mos
script how many ticks to add
to the beginning of the score (which presumably has the pick-up beat as
delta-time zero) to make a complete measure, so that the measure count
is correctly aligned. In this situation the script actually makes up the
measure with negative ticks, thus maintaining the tick alignment of the
original MIDI file.
At the standard rate of 96 pulses per quarternote (ppqn 96) Quarternote = 96, Halfnote = 192, Wholenote = 384 Eighthnote = 48, Sixteenthnote = 24, Thirtysecondnote = 12 4/4 time: = 384, a = 288 for quarternote pick-up 3/4 time: = 288, a = 192 for quarternote pick-up 3/4 time: = 288, a = 288 no pick-up note 6/8 time: = 288, a = 240 for eighthnote pick-up 12/8time: = 576, a = 528 for eighthnote pick-up (The ppqn is recorded at line 4 in mid2txt output files.)
Using the -a switch will probably require the -b switch as well, because the default first measure is set to 1 and having used the -a switch, the first measure is nominally measure zero. If the score begins at measure 1, none of the above is necessary. However, the -b switch is also useful for preserving the measure numbering where the score or segment of score begins beyond m1. Assuming time signature information is included in the MIDI file, the txt2mos script will automatically set the measure length to begin with and adjust the measure count to accommodate for changes of time signature encountered within the score.
The granularity of tick division is read automatically from the MIDI file and if this information is missing from the file it is set by default to the common 96 ticks per quarternote. In the rare situation where a different division (e.g. 120 ppq) has been used but is not recorded in the MIDI data the -d switch can be used.
The -k switch sets an arbitrary fundamental period (H1), specified by pitch-class C0 through B11 or negative MIDI note number. Although the txt2mos script will always calculate and record the natural period of the input music data, often this will not be the same as the key/tonal center. There are four possibilities:
1) If the -k switch is absent from the txt2mos
command the
natural period is used as the unit (H1) fundamental.
2) If the -k switch is used without a parameter attached, the
txt2mos
script will read the last occurring key signature
data in the file and set the unit (H1) fundamental to the key letter
(pitch class) for major keys or to a major-third below the key letter
for minor keys. An appropriate frequency level for the unit fundamental
will be chosen so as to maintain whole numbered relationships
throughout.
3a) The -k switch can also be used with either of two parameters: a positive number in the pitch class range C-B, 0 to 11 or a negative MIDI note number. The former positive numbers 0 through 11 can be used where no key signature data is in the file, or alternatively, to override key signature data that is in the file. Care is needed: all key-tones are viewed as single acoustic entities (e.g. Gflat major is -k6, i.e. F#) and accommodation should normally be made for the minor key nesting in a series a major-third below its key-letter pitch class (e.g. G minor is -k3, i.e. D#).
3b) Negative MIDI note numbers in the range -1 through -60 (written -k-n, hyphen for minus sign and no white space) are used to explicitly set the key-letter pitch class and frequency level of the unit fundamental (e.g. -k-24, sets the unit to C two octaves below MIDI note number zero). Count down chromatically from C zero to find the number required: C0, B-1, A#-2, A-3, etc. In the highly unlikely situation that a non-negative MIDI note level is required one of the earlier options should achieve this.
If there is no time signature information the -m switch is used to inform the script of the measure length. The default is 4/4 common time - 384 ticks at 96 ticks per quarternote. There is no facility for making the -m switch effect a time signature change within the body of the score, although this could be achieved by inserting time signature information directly into the score list beforehand.
The -o switch prints an overview of the chords and conjunction at the end of the output as a succession of comments.
The -r switch restricts the display of redundant slices.
The script automatically introduces a degree of smoothing out of the intervals between adjacent nested harmonic series, which is turned off by giving the -s switch. Because the txt2mos script finds the first/highest appropriate nested harmonic series and preserves these positions because of their importance for chord recognition (Beament, 2005), this can produce a jagged profile between adjacent series. Thus, a simple smoothing algorithm is used to double or occasionally quadruple the period of nested series so as to produce a more coherent flow of middle level exchanges. These octave extensions to the nested series are marked 'h===...'.
Finally, the -w switch sets the slice width, the default is 48 ticks which is equivalent to an eighthnote at a tick division of 96.
For more information on the use of the txt2mos
see
Journey to the Heart of Music, Chpt21 Appendix F, from page 4
onward available from http://www.pjperry.freeuk.com/ by following the
links.
newH1
Usage: [perl] newH1 [-h -k<n>] amended_txt2mos_output
[> myfile]
NOTE This script requires access to the database files:
- mosmbn.dir
- mosmbn.pag
Example
- -k-24 reset absolute fundamental H1 and recalculate MBN, default natural period
The -k switch sets an arbitrary fundamental period (H1), specified by
pitch-class C0 through B11 or negative MIDI note number. Although the
txt2mos
script will always calculate and record the
natural period of the input music data, often this will not be the
same as the key/tonal center. There are four possibilities:
1) If the -k switch is absent from the txt2mos
command the
natural period is used as the unit (H1) fundamental.
2) If the -k switch is used without a parameter attached, the
txt2mos
script will read the last occurring key signature
data in the file and set the unit (H1) fundamental to the key letter
(pitch class) for major keys or to a major-third below the key letter
for minor keys. An appropriate frequency level for the unit fundamental
will be chosen so as to maintain whole numbered relationships
throughout.
3a) The -k switch can also be used with either of two parameters: a positive number in the pitch class range C-B, 0 to 11 or a negative MIDI note number. The former positive numbers 0 through 11 can be used where no key signature data is in the file, or alternatively, to override key signature data that is in the file. Care is needed: all key-tones are viewed as single acoustic entities (e.g. Gflat major is -k6, i.e. F#) and accommodation should normally be made for the minor key nesting in a series a major-third below its key-letter pitch class (e.g. G minor is -k3, i.e. D#).
3b) Negative MIDI note numbers in the range -1 through -60 (written -k-n, hyphen for minus sign and no white space) are used to explicitly set the key-letter pitch class and frequency level of the unit fundamental (e.g. -k-24, sets the unit to C two octaves below MIDI note number zero). Count down chromatically from C zero to find the number required: C0, B-1, A#-2, A-3, etc. In the highly unlikely situation that a non-negative MIDI note level is required one of the earlier options should achieve this.
The script newH1 can be used to set a new unit H1 and automatically
recalculate the absolute fundamental series as represented in the factor
format mutable base numbers in the txt2mos
file.
If the negative MIDI note number parameter is not low enough to allow for whole numbered relationships, the script exits after printing a warning message quoting the lowest nested series h1 that is incompatible with the chosen absolute fundamental H1.
For more information: http://www.pjperry.freeuk.com/ Journey to the Heart of Music, Chpt19 and Chpt21.
mos2col
Usage: [perl] mos2col [-f -h -p<n>]
amended_txt2mos_output [> myfile]
NOTE This script requires access to the database files:
- mosmbn.dir
- mosmbn.pag
Example
- -f fixed equal-temperament frequency grid
- -p1.022 adjust the pitch standard to A=440Hz, default pitch middle C=256Hz
The -p switch is used to adjust the written pitch in the column data to whatever level is required. The default (or with the switch -p1) pitches are written at the level of middle C=256Hz. By giving the -p switch a decimal fraction greater or lesser than 1, the pitch level may be adjusted up or down. As in the example, 256 1.022 = 261.6, approximately the pitch of middle C at A=440Hz. Longer fractional expansions may be used if greater accuracy is required, however, it should be noted that quite soon any normally complex harmonic progression will wander away from its opening pitch level as the algorithm of symmetrical exchange computes the whole number ratios.
If on the other hand a fixed frequency grid is desired, the -f switch can be used to force the output to adhere to equal-temperament at whatever pitch level is chosen.
For more information on the use of the mos2col
see
Journey to the Heart of Music, Chpt21 Appendix F, from page 14
onward available from http://www.pjperry.freeuk.com/ by following the
links.
txt2inv
Usage: mid2inv [-a<n> -h -k<n>] input-text-file
- -a<n> MIDI note-number axis of rotation.
- -h print help/usage message.
- -k when used on its own it changes the default major to minor key-shift to the reverse.
Output is to STDOUT, which can be redirected to file:
eg. midinvert -a55 -k input-text-list > output-text-file
would send an inverted score (note) list to the output file (or full path) specified - rotation axis G55, minor to major.
The input score list must be of a format produced by mid2txt
-i.e. generated by the Perl-MIDI modules written by Sean Burke and freely available from CPAN - which require Perl 5.001 or above. By default middle C60 is the rotational axis, this can be changed using the -a switch to specify another MIDI note number eg. -a65 for F above middle C60. Any out of range rotations (beyond 0-127) are 8ve shifted into range. Also by default the key-shift is major to minor eg. from C-major to A-minor for the inverted piece, using the -k switch reverses this default shift for minor to major inversions. The inverted score list output by mid2inv
can be turned back to MIDI format using txt2mid and then loaded into a music editor or sequencer.
Returning yet again to Bach's chorale setting, the first bar seen above as output from mid2txt
is transformed into the score list below. Notice that the key_signature parameter three has been converted to '1' indicating A-minor and the first chord (which above was root position C-major, MIDI note-numbers: 48C, 64E, 67G and 72C) is below a second inversion A-minor chord: 52E, 57A, 60C and 76E. This transformation encapsulates the concept of 'reflecting' an harmonic series, by strict inversion, into an arithmetic series - an inverted or 'descending' harmonic series.
MIDI file output in plain text:
MThd (6 bytes)
Format 1 (2 tracks)
Metrical time (TickDiv = 96 ppqn)
Track: 0
@notes = ( # 2 notes...
['key_signature', 0, 0, 1],
['time_signature', 0, 4, 2, 24, 8],
['set_tempo', 72, 1000000],
);
Track: 1
@notes = ( # 152 notes...
['control_change', 288, 0, 0, 0],
['control_change', 288, 0, 32, 0],
['patch_change', 288, 0, 0],
['control_change', 288, 0, 10, 64],
['control_change', 288, 0, 91, 61],
['note', 288, 96, 0, 57, 74],
['note', 288, 96, 0, 52, 78],
['note', 288, 96, 0, 76, 76],
['note', 288, 96, 0, 60, 78],
['note', 384, 96, 0, 57, 75],
['note', 384, 96, 0, 53, 75],
['note', 384, 96, 0, 69, 78],
['note', 384, 96, 0, 62, 78],
['note', 480, 96, 0, 58, 69],
['note', 480, 96, 0, 55, 67],
['note', 480, 48, 0, 74, 76],
['note', 480, 48, 0, 62, 78],
['note', 528, 48, 0, 74, 69],
['note', 528, 48, 0, 64, 72],
['note', 576, 96, 0, 62, 64],
['note', 576, 96, 0, 57, 68],
['note', 576, 96, 0, 81, 63],
['note', 576, 96, 0, 65, 70],
['note', 672, 48, 0, 60, 68],
['note', 672, 48, 0, 57, 75],
['note', 672, 48, 0, 76, 88],
['note', 672, 48, 0, 64, 78],
['note', 720, 48, 0, 62, 69],
['note', 720, 48, 0, 57, 73],
['note', 720, 48, 0, 76, 72],
['note', 720, 48, 0, 66, 68],
['note', 768, 96, 0, 64, 82],
['note', 768, 96, 0, 55, 87],
['note', 768, 48, 0, 71, 74],
['note', 768, 48, 0, 67, 74],
etc...
);
txt2ret
Usage: [perl] txt2ret [-h -t<n,m>] score-list-file
- -h print help/usage message.
- -t<n, > = ticks in bar.
- < ,m> = offset fzom start of 'bar zero' to pick-up note/chord (m = ticks-in-bar minus ticks-in-pick-up-note/chord)
A full notional 'bar zero' containing any pick-up note/chord precedes bar one, for pieces starting at the beginning of bar one this notional bar zero is empty (thus: m = n - 0 or -t384,384) this is the default, no pick-up note/chord, the -t switch is not required for these pieces . In fact, only the 'm' value - the tick offset before first note/chord - is of significance to the output of the script: it provides a means of moving the retrograde form between varying beat positions, as a compostion might begin with a short note/chord and end with a long note/chord (see below).
Output is to STDOUT, which can be redirected to file:
eg. txt2ret score-list-file > retrograde-score-list-file
would send an retrograde score (note) list to the output file (or full path) specified.
The input score list (not event list) must be in the format produced by mid2txt
-i.e. generated by the Perl-MIDI modules and contain multiple note data tracks. The retrograde score list output can be turned back to MIDI format using txt2mid
and then loaded into a music editor or sequencer.
txt2ret
returns a score list in retrograde order. Staying with the above example chorale, the end of the reversed track (below the cut-->), contains the original first five beats of the compostion, while also shown is the beginning of the track - now containing the last chord:
MIDI file output in plain text:
MThd (6 bytes)
Format 1 (2 tracks)
Metrical time (TickDiv = 96 ppqn)
Track: 0
@notes = ( # 3 notes...
['key_signature', 0, 0, 0],
['time_signature', 0, 4, 2, 24, 8],
['set_tempo', 72, 1000000],
);
Track: 1
@notes = ( # 152 notes...
['control_change', 288, 0, 0, 0],
['control_change', 288, 0, 32, 0],
['patch_change', 288, 0, 0],
['control_change', 288, 0, 10, 64],
['control_change', 288, 0, 91, 61],
['note', 288, 96, 0, 64, 80],
['note', 288, 96, 0, 72, 80],
['note', 288, 96, 0, 48, 71],
['note', 288, 96, 0, 55, 71],
cut-------------------------->
['note', 2832, 48, 0, 53, 74],
['note', 2832, 48, 0, 57, 74],
['note', 2880, 48, 0, 62, 69],
['note', 2880, 48, 0, 67, 73],
['note', 2880, 48, 0, 48, 72],
['note', 2880, 48, 0, 58, 68],
['note', 2928, 48, 0, 64, 68],
['note', 2928, 48, 0, 67, 75],
['note', 2928, 48, 0, 48, 80],
['note', 2928, 48, 0, 60, 78],
['note', 2976, 96, 0, 62, 64],
['note', 2976, 96, 0, 67, 68],
['note', 2976, 96, 0, 43, 63],
['note', 2976, 96, 0, 59, 70],
['note', 3072, 96, 0, 66, 69],
['note', 3072, 96, 0, 69, 67],
['note', 3072, 48, 0, 50, 69],
['note', 3072, 48, 0, 60, 72],
['note', 3120, 48, 0, 50, 76],
['note', 3120, 48, 0, 62, 78],
['note', 3168, 96, 0, 67, 75],
['note', 3168, 96, 0, 71, 75],
['note', 3168, 96, 0, 55, 78],
['note', 3168, 96, 0, 62, 78],
['note', 3264, 96, 0, 67, 74],
['note', 3264, 96, 0, 72, 78],
['note', 3264, 96, 0, 48, 76],
['note', 3264, 96, 0, 64, 78],
);
The above result was obtained using the switch -t384,288
, the 288 empty ticks at the beginning were crucial in that without them the first few notes would occur before the control_change
commands. However, if the switch -t384,384
was given, the whole piece would have been shifted by one quarternote so as to begin on the beat.
txt2txt
Usage: [perl] txt2txt [-c<s2e|e2s|s2z|s2c<opt>> -h] input-textfile
-c conversion switch, requires s2e, e2s or s2z as arguments: score-list to event-list, event-list to score-list or (type one - multi-track) score-list to (type zero - single track) score-list. The input data must be consistent with the argument given, for example s2z requires a score-list and not an event-list.
Output is to STDOUT, which can be redirected to file: eg. txt2txt -cs2e input-textfile > output-textfile would convert a score list to an event list, sending the output to the file specified. A type 0 event list needs two or three sequential runs: -ce2s -cs2z -cs2e
The s2c
would produce a text list of MIDI note numbers sounding at elapse times
0, 96, 192, 288, etc.., that is every quarternote given the usual
tick division of 96ppqn - 96 pulses per quaternote. Another, less
common tickdiv is 120ppqn. The script reads the tickdiv from the
scorelist header.
txt2txt -cs2c96 input-textfile > out-putfile
By default -i.e. no -c switch given, the script scans the input file for errors and outputs a description of any found. At present only a scan for negative deltatimes is made - a feature sometimes produced by the original Acorn/RISC OS version of Sibelius. After which the user is presented with a Y/N choice to fix the data or exit:
txt2txt myscore-list-file
Track 2, negative number: ['note', 384, -384, 0, 63, 95],
Track 2, negative number: ['note', 1536, -1536, 0, 65, 95],
Track 2, negative number: ['note', 2880, -2880, 0, 58, 94],
Fix error(s), Y/N?
Y /home/mydir/myfile
Anything after 'Y' or 'y' is taken to be the output file path. If no
file name or path is specified the default is a file 'Sibfix' in the
currently selected/working directory. The script cannot know the
correct duration and so examines neighbouring notes beginning at the
same moment and adopts the shortest duration found amongst them. It
corrects both negative and zero durations which Sib7 (v3.5) produces
in pairs.
The script uses the MIDI-perl modules written by Sean Burke (which require Perl 5.001 or above) - available from CPAN.
txtconcat
Usage: [perl] txtconcat <txtfile1> <txtfile2> ...
(Output is to STDOUT) -h Print this help message -d Prints verbose Info messages (for debug only) -pPulses per quarternote (default: first mid2txt value) (event time values are scaled to the -p value)
Description:
Concatenates mid2txt files (score list) by adjusting the event
times to start at the end of the preceding file's measure as follows:
- track0 = file1-track0 + file2-track0 + file3-track0 + ... - track1 = file1-track1 + file2-track1 + file3-track1 + ... - etc.
The files can have differing numbers of tracks. If there are no events in combined track, then that track will be suppressed in the output.
The files can have differing ppqn (pulses per quarter note) values. By default the first file's ppqn will be used for all files. The -p option can be used to supply a common ppqn to be used. A file's event times are normalized to the ratio of the common ppqn to the file's ppqn.
The txtconcat script was written by David C. and the author has generously allowed it to be included here. David can be contacted at dkcasset@gmail.com
Limitatons:
- Currently only supports MIDI Type 1 files.
- Currently only score list (note events) are supported. Event list (mid2txt's -e option using note_on / note_off events) is not supported.
- No events are added to the output. Some events might need to be manually added, for example, if SoundFont bank 42 is used by file1 but file2 uses General Midi bank 0 (but doesn't have the control_change event for bank0), then file2 will continue to use bank 42. In this case the control_change will need to be added.
- There are probably many more unforseen side effects that may be encountered (e.g. if the track name changes from one file to another, the sequencer may only display the first track name).
txt2mid
Usage: [perl] txt2mid [-e -f<filename> -h -p<ppqn> -t<n>] input-file
The default output filename (in cwd) is: txt2mid_MID
, the -f switch can be used to change this to a different (path and) filename. (No space between -f and filename and/or "" around filename.)
By default txt2mid expects input in score list format, that is a note list of starttime + duration form. The -e switch changes this default to an event list of note_on and note_off events. By default the division is 96 (pulses per quarternote). The -p switch can be used to change this - as above no spaces or "". And the final default is MIDI type or format '1', which can be changed to type '0' (single track format) with the -t switch. This script reads a textual description of music in MIDI score list format (from mid2txt) or event list format (from mid2txt with -e switch) and converts the text list into a MIDI file via the services of the MIDI-perl modules.
Note: The input text data must be consistent with the switches used. For example, -t0 works only if the input data is all in one track and simply specify -p120 for a text list of division 96ppqn will create a MIDI file with internal inconsistencies.
canon
A script which searches through a piece of music, a sequence of of chords, for a canon at a given pitch and time interval.
Usage: [perl] canon [-h -p<semitones> -t<ticks>] input-textfile
-h help, -p pitch interval of canon, -t time interval of canon.
The input text file must be of the form generated by the script
txt2txt with the -cs2c switch set, that is a text list of bar
numbers, elapse times and MIDI note numbers. Eg:
BarNum PollTick NoteNumbers...
1.50 192 50 66 69 74 78
The input data is scanned for a potential canon at the time interval in ticks and the pitch interval in semitones specified by the -p and -t switches. The defaults are time -t384 ticks (four quarternotes at the common tick division of 96ppqn and pitch -p0, a canon at a unison or octave interval. Pitch intervals of a fourth -p5 and fifth -p7 are common choices but any number 0-11 will work.
Output is to STDOUT, which can be redirected to file, eg:
canon -t192 -p7 input-textfile > output-textfile
would look for canon at the fifth and separated by two quarternotes
(assuming 96 pulses per quarternote) sending the output to the
file specified. The canon script will only process one input file
per run, multiple input files will overwrite each other.
In use the script will quickly run through a number of likely or desired pitch and time intervals applied to a single output file from txt2txt. On the basis of these result a judgement can be made as to which time and pitch intervals present the richest possibilities. For printing the output, the elapse times can all be sheared off in one operation by a text editor -- if not required; and the bar plus note information load into a multi-column template in a word processor.
baseN
Outputs digit sequences of fixed base number systems from base2 through base36, with decimal equivalent.
Usage: [perl] baseN -n<number> -b<number>
-i.e. perl baseN -n256 -b2
will output 0 to 255 numbers in binary (base2) and decimal format.
Usage: [perl] digseq -h
Numbers output are padded with leading zeros, with individual digits separated by spaces. Depending on the particular combination of (-n)number and (-b)base, a leading column of zeros may be appended to the output. In addition to the digits 0 through 9, the letters A through Z are used in numbers with bases above ten, as required. Redirection ( > myfile ) can be used to send output to file.
digseq
The script finds the number of possible and distinguishable digit sequences of the given mutable number, that is, all the nested configurations of a mutable base number (abr. MBN). For example, the mutable base number thirty (the harmonic series h1 through h30) can be accessed by six alternative three-column digit sequences: 5x3x2 (i.e. h1,2,3,4,5 nesting h10,h15 nesting h30 - ground state), 5x2x3, 3x5x2, 3x2x5, 2x5x3 and 2x3x5, as well as five alternative 'multiplied out' sequences: 15x2, 2x15, 6x5, 5x6 and 1x30 (h1 through h30 - prime state); each physically distinguishable.
First the script works out the divisors and prime factors of the mutable number (specified in the command as a decimal number). Next the script generates all the possible intermediate combinations which lie between the divisor pairs and the prime factors. Finally the script works out the total number of permutations of these combinations and more crucially the number of distinguishable arrangements -- that is valid mutable base digit sequences.
Output is to STDOUT, which can be redirected to file:
eg. [perl] digseq -n10080 > myfile
would send the list of the number of distinguishable digit
sequences to the output file or full path specified.
As a great variety of computational power abounds, it maybe a good idea to start with smaller numbers to gauge time scales vis-a-vis number. It is not so much the magnitude of the number itself but the number of factors and therefore columns, which multiply the range of potential digit sequences the script has to sift -i.e. 2592 (2x2x2x2x2x3x3x3x3) has up to nine columns, while 2951, a prime, has one column. The algorithm used to find the divisors and factors relies on the feature of 'bow waves' found in the Sieve of Eratosthenes and described in chapter seven of 'Journey to the Heart of Music'.
divisor
A script which find the divisors of positive odd and even whole numbers.
Usage: [perl] divisor -n<number> [-h]
Output is to STDOUT, which can be redirected to file:
eg. [perl] divisor -n10080 > myfile
eg. [perl] divisor -n12347 > home/mydivisors
would send the list of divisors to the output file or
full path specified.
As a great variety of computational power abounds, it maybe a good idea to start with smaller numbers to gauge time scales vis-a-vis number size. The algorithm relies on the feature of 'bow waves' found in the Sieve of Eratosthenes and described in chapter seven of 'Journey to the Heart of Music'.
tacker
Another script which find the divisors of positive odd and even whole numbers.
Usage: [perl] divisor -n<number> [-h]
Output is to STDOUT, which can be redirected to file:
eg. [perl] tacker -n12121 > myfile
eg. [perl] tacker -n32124 > home/mydivisors
would send the list of divisors to the output file or
full path specified.
As a great variety of computational power abounds, it maybe a good idea to start with smaller numbers to gauge time scales vis-a-vis number size. The algorithm used by the script relies on the feature of 'tacking' down rows found in the Table of Nested Harmonic Series or Sieve of Eratosthenes as described in 'Journey to the Heart of Music'. This script is far less efficient than 'divisor' and is included here for completeness.
Click here to download the scripts: perl scripts plus manuals in a ZIP archive (94Kb).
Click here to download the awk HTML sorting script, entity mapping file and brief instructions.