protected void ApplyHaltEffect(Song s, Dictionary<Pattern, RowFxData[,]> patternFxData) { // Find the first Cxx effect and truncate the song. for (int p = 0; p < s.Length; p++) { for (int c = 0; c < s.Channels.Length; c++) { var pattern = s.Channels[c].PatternInstances[p]; var patternLength = s.GetPatternLength(p); if (patternFxData.TryGetValue(pattern, out var fxData)) { for (int i = 0; i < fxData.GetLength(0) && i < patternLength; i++) { for (int j = 0; j < fxData.GetLength(1); j++) { var fx = fxData[i, j]; if (fx.fx == Effect_Halt) { if (s.PatternHasCustomSettings(p)) s.GetPatternCustomSettings(p).patternLength = i + 1; else s.SetPatternCustomSettings(p, i + 1, s.BeatLength); s.SetLength(p + 1); s.SetLoopPoint(-1); return; } } } } } } }
private void ExtendSongForLooping(Song song, int loopCount) { // For looping, we simply extend the song by copying pattern instances. if (loopCount > 1 && song.LoopPoint >= 0 && song.LoopPoint < song.Length) { var originalLength = song.Length; var loopSectionLength = originalLength - song.LoopPoint; song.SetLength(Math.Min(Song.MaxLength, originalLength + loopSectionLength * (loopCount - 1))); var srcPatIdx = song.LoopPoint; for (var i = originalLength; i < song.Length; i++) { foreach (var c in song.Channels) { c.PatternInstances[i] = c.PatternInstances[srcPatIdx]; } if (song.PatternHasCustomSettings(srcPatIdx)) { var customSettings = song.GetPatternCustomSettings(srcPatIdx); song.SetPatternCustomSettings(i, customSettings.patternLength, customSettings.beatLength, customSettings.groove, customSettings.groovePaddingMode); } if (++srcPatIdx >= originalLength) { srcPatIdx = song.LoopPoint; } } } }