mirror of
https://github.com/vsariola/sointu.git
synced 2025-05-28 03:10:24 -04:00
50 lines
1.6 KiB
Go
50 lines
1.6 KiB
Go
package sointu
|
|
|
|
// Score represents the arrangement of notes in a song; just a list of tracks
|
|
// and RowsPerPattern and Length (in patterns) to know the desired length of a
|
|
// song in rows. If any of the tracks is too short, all the notes outside the
|
|
// range should be just considered as holding the last note.
|
|
type Score struct {
|
|
Tracks []Track
|
|
RowsPerPattern int // number of rows in each pattern
|
|
Length int // length of the song, in number of patterns
|
|
}
|
|
|
|
// Copy makes a deep copy of a Score.
|
|
func (l Score) Copy() Score {
|
|
tracks := make([]Track, len(l.Tracks))
|
|
for i, t := range l.Tracks {
|
|
tracks[i] = t.Copy()
|
|
}
|
|
return Score{Tracks: tracks, RowsPerPattern: l.RowsPerPattern, Length: l.Length}
|
|
}
|
|
|
|
// NumVoices returns the total number of voices used in the Score; summing the
|
|
// voices of every track
|
|
func (l Score) NumVoices() int {
|
|
ret := 0
|
|
for _, t := range l.Tracks {
|
|
ret += t.NumVoices
|
|
}
|
|
return ret
|
|
}
|
|
|
|
// FirstVoiceForTrack returns the index of the first voice of given track. For
|
|
// example, if the Score has three tracks (0, 1 and 2), with 1, 3, 2 voices,
|
|
// respectively, then FirstVoiceForTrack(0) returns 0, FirstVoiceForTrack(1)
|
|
// returns 1 and FirstVoiceForTrack(2) returns 4. Essentially computes just the
|
|
// cumulative sum.
|
|
func (l Score) FirstVoiceForTrack(track int) int {
|
|
ret := 0
|
|
for _, t := range l.Tracks[:track] {
|
|
ret += t.NumVoices
|
|
}
|
|
return ret
|
|
}
|
|
|
|
// LengthInRows returns just RowsPerPattern * Length, as the length is the
|
|
// length in the number of patterns.
|
|
func (l Score) LengthInRows() int {
|
|
return l.RowsPerPattern * l.Length
|
|
}
|