
christopher@51: \section{Framework}
christopher@51: 
christopher@51: \begin{figure}[t]
christopher@51: \centering
christopher@62: \includegraphics[width=0.95\columnwidth]{images/framework.pdf}
christopher@62: \caption{Module hierarchy in the synpy toolkit: the top-level module provides a simple interface for the user to test different syncopation models. Musical constructs such as bars, velocity and note sequences, notes and time-signatures are defined in the `music objects' module; support for common procedures such as sequence concatenation and subdivision is provided in `basic functions'. Models and file reading components can be chosen as required by the user.\label{fig:framework}}
christopher@51: \end{figure}
christopher@51: 
christopher@62: The architecture of the toolkit is shown in Figure~\ref{fig:framework}. Syncopation values can be calculated for each bar in a given source of rhythm data along with selected statistics over all bars; the user specifies which model to use and supplies any special parameters that are required. Sources of rhythm data can be a bar object or a list of bars (detailed below in section~\ref{sec:musicobjects}) or, alternatively, the name of a file containing music data. Where a model is unable to calculate a value for a given rhythm pattern, a `None' value is recorded for that bar and the indices of unmeasured bars reported in the output.  If no user parameters are specified, the default parameters specified in the literature for each model are used. Output can optionally be saved directly to XML or JSON files. An example of usage in the Python interpreter is shown in Figure~\ref{ta:example}.
christopher@59: 
christopher@59: \begin{figure}
christopher@59: \footnotesize{
christopher@59: \begin{minted}[frame=single,framesep=10pt]{python}
christopher@59: >>>from synpy import *
christopher@59: >>>import synpy.PRS as model
christopher@62: >>>calculate_syncopation(model, "clave.rhy", 
christopher@62:    outfile="clave.xml")
christopher@59: {'bars_with_valid_output': [0, 1],
christopher@59:  'mean_syncopation_per_bar': 8.625,
christopher@59:  'model_name': 'PRS',
christopher@59:  'number_of_bars': 2,
christopher@59:  'number_of_bars_not_measured': 0,
christopher@59:  'source': 'clave.rhy',
christopher@59:  'summed_syncopation': 17.25,
christopher@59:  'syncopation_by_bar': [8.625, 8.625]}
christopher@59: \end{minted}
christopher@59: }
christopher@62: \caption{To use the toolkit, the top level \code{synpy} module is imported along with a model (in this example Pressing \cite{Pressing97}). Calling \code{calculate\_syncopation()} then gives the syncopation results as shown, writing output to an XML file. Output file names and extra parameters for a model are added as optional arguments as required by the user. 
christopher@59: \label{ta:example} }
christopher@59: \end{figure}
christopher@54: 
christopher@54: \subsection{Music objects}
christopher@54: \label{sec:musicobjects}
christopher@62: The `music objects' module provides classes to represent the musical constructs described in Section~\ref{sec:background}.  A \code{Bar} object holds the rhythm information for a single bar of music along with its associated time-signature and optional tempo and TPQ values (see Section~\ref{sec:background:rhythm:timespan}). \code{Bar} objects may be initialised with either a note sequence or velocity sequence and can be chained together in the form of a doubly-linked \code{BarList} allowing syncopation models to access next and previous bars where appropriate\footnote{Several models \cite{LHL84,Keith91,Pressing97,Gomez05} implemented in the toolkit require knowledge of the contents of previous and/or next bars in order to calculate the syncopation of the current bar.}. The note sequence and velocity sequence classes are direct implementations of the sequences described in Section~\ref{sec:background:rhythm:note}.    Common low-level procedures such as sequence concatenation and subdivision are provided in `basic functions'.
christopher@54: 
christopher@54: \subsection{File Input}
christopher@54: \label{sec:fileinput}
christopher@54: Two file reader modules are currently provided: one for for reading plain text rhythm annotation (\code{.rhy}) files and one for reading standard MIDI files (\code{.mid}). These modules open their respective file types and return a \code{BarList} object ready for processing.  
christopher@54: 
christopher@51: \begin{figure}
christopher@51: \footnotesize{
christopher@51: \begin{minted}[frame=single,framesep=10pt]{python}
christopher@62: T{4/4} # time-signature
christopher@51: TPQ{4} # ticks per quarternote
christopher@51: # Bar 1
christopher@51: Y{(0,3,2),(3,1,1),(6,2,2),(10,2,1),(12,4,1)}
christopher@51: # Bar 2
christopher@51: V{1,0,0,0.5,0,0,1,0,0,0,0.5,0,0.5,0,0,0}
christopher@51: \end{minted}
christopher@51: }
christopher@54: \caption{Example rhythm annotation \code{.rhy} file containing two bars of the Son Clave rhythm. The first is expressed as a note sequence with resolution of four ticks per quarternote; the second is the same rhythm expressed as a velocity sequence (see section~\ref{sec:background}).}
christopher@51: \label{ta:clave} 
christopher@51: \end{figure}
christopher@62: Our \code{.rhy} annotation format is a light text syntax for descibing rhtyhm patterns directly in terms of note and velocity sequences (see Figure~\ref{ta:clave}). The full syntax specification is given in Backus Naur Form on the toolkit page \cite{Song14URL}.
christopher@55: 
christopher@62: The MIDI file reader can open type 0 and type 1 standard MIDI files and select a given track to read rhythm from.  Notes with zero delta time between them (i.e. chords) are treated as the same event for the purposes of creating note sequences from the MIDI stream. Time-signature and tempo events encoded in the MIDI stream are assumed to correctly describe those parameters of the recorded music so it is recommended that the user uses correctly annotated and quantised MIDI files.
christopher@54: 
christopher@54: \subsection{Plugin architecture}
christopher@54: The system architecture has been designed to allow new models to be added easily.   Models have a common interface, exposing a single function that will return the syncopation value for a bar of music.  Optional parameters may be supplied as a Python dictionary if the user wishes to specify settings different from the those given in the literature for a specific model.
christopher@54: 
christopher@51: 
christopher@51: 
christopher@51: 
christopher@51: 
christopher@51: 
christopher@51: 
christopher@51: % \section{MIDI Input}\label{sec:midi}
christopher@51: 
christopher@51: % \cite{Taylor89MusicTheory}
christopher@51: 
christopher@51: % \section{Text Input}\label{sec:textinput}
christopher@51: 
christopher@51: % \begin{table*}
christopher@51: % \small{
christopher@51: % \begin{minted}[frame=single,framesep=10pt]{console}
christopher@51: % <piece>             ::=  [<comment-lines>] <timesig> <line> | <piece> <line>
christopher@51: 
christopher@51: % <comment-lines>     ::= <comment> "\n" | <comment-lines> <comment> "\n"
christopher@51: 
christopher@51: % <line>              ::= [<barlist>] [<comment>] "\n"
christopher@51: 
christopher@51: % <comment>           ::= "#" <comment-text>
christopher@51: 
christopher@51: % <barlist>           ::= <time-info> | [<time-info>] <bar> | <barlist> <bar>
christopher@51: 
christopher@51: % <time-info>         ::= [<timesig>] [<ticks-per-quarter>] [<tempo>] 
christopher@51: 
christopher@51: % <tempo>             ::= "QPM{" <digits> "}"
christopher@51: 
christopher@51: % <ticks-per-quarter> ::= "TPQ{" <digits> "}"
christopher@51: 
christopher@51: % <timesig>           ::= "T{" <digit> "/" <digit> "}"
christopher@51: 
christopher@51: % <bar>               ::= "V{" <velocity-sequence> "}" | "Y{" <note-sequence> "}"
christopher@51: 
christopher@51: % <note-sequence>     ::= <note> | <note-sequence> "," <note>
christopher@51: 
christopher@51: % <note>              ::= "(" <digits> "," <digits> "," <digits> ")"
christopher@51: 
christopher@51: % <velocity-sequence> ::= <decimal> | <velocity-sequence> "," <decimal>
christopher@51: 
christopher@51: % <decimal>           ::= "0" | "1" | "0." <digits>
christopher@51: 
christopher@51: % <digits>            ::= <digit> | <digits> <digit>
christopher@51: 
christopher@51: % <digit>             ::= "0" | "1" | "2" | "3" | "4" | "5" | "6" | "7" | "8" | "9"
christopher@51: % \end{minted}
christopher@51: % }
christopher@51: % \caption{Syntax of rhythm text format Backus-Naur Form}
christopher@51: % \label{ta:BNF} 
christopher@51: % \end{table*}
christopher@51: 
christopher@51: 




