public void TestHoldNoteWithReleasePress() { // | | | // | * | - | // | * | | // | * | | // | | | var beatmap = new ManiaBeatmap(new StageDefinition { Columns = 2 }); beatmap.HitObjects.Add(new HoldNote { StartTime = 1000, Duration = 2000 }); beatmap.HitObjects.Add(new Note { StartTime = 3000, Column = 1 }); var generated = new ManiaAutoGenerator(beatmap).Generate(); Assert.AreEqual(generated.Frames.Count, frame_offset + 3, "Incorrect number of frames"); Assert.AreEqual(1000, generated.Frames[frame_offset].Time, "Incorrect first note hit time"); Assert.AreEqual(3000, generated.Frames[frame_offset + 1].Time, "Incorrect second note press time + first note release time"); Assert.AreEqual(3000 + ManiaAutoGenerator.RELEASE_DELAY, generated.Frames[frame_offset + 2].Time, "Incorrect second note release time"); Assert.IsTrue(checkContains(generated.Frames[frame_offset], ManiaAction.Key1), "Key1 has not been pressed"); Assert.IsFalse(checkContains(generated.Frames[frame_offset + 1], ManiaAction.Key1), "Key1 has not been released"); Assert.IsTrue(checkContains(generated.Frames[frame_offset + 1], ManiaAction.Key2), "Key2 has not been pressed"); Assert.IsFalse(checkContains(generated.Frames[frame_offset + 2], ManiaAction.Key2), "Key2 has not been released"); }
public void TestHoldNoteChord() { // | | | // | * | * | // | * | * | // | * | * | // | | | var beatmap = new ManiaBeatmap(new StageDefinition { Columns = 2 }); beatmap.HitObjects.Add(new HoldNote { StartTime = 1000, Duration = 2000 }); beatmap.HitObjects.Add(new HoldNote { StartTime = 1000, Duration = 2000, Column = 1 }); var generated = new ManiaAutoGenerator(beatmap).Generate(); Assert.IsTrue(generated.Frames.Count == 3, "Replay must have 3 frames"); Assert.AreEqual(1000, generated.Frames[1].Time, "Incorrect hit time"); Assert.AreEqual(3000 + ManiaAutoGenerator.RELEASE_DELAY, generated.Frames[2].Time, "Incorrect release time"); Assert.IsTrue(checkContains(generated.Frames[1], ManiaAction.Key1, ManiaAction.Key2), "Key1 & Key2 have not been pressed"); Assert.IsFalse(checkContains(generated.Frames[2], ManiaAction.Key1, ManiaAction.Key2), "Key1 & Key2 have not been released"); }
public void TestHoldNoteStair() { // | | | // | | * | // | * | * | // | * | * | // | * | | // | | | var beatmap = new ManiaBeatmap(new StageDefinition { Columns = 2 }); beatmap.HitObjects.Add(new HoldNote { StartTime = 1000, Duration = 2000 }); beatmap.HitObjects.Add(new HoldNote { StartTime = 2000, Duration = 2000, Column = 1 }); var generated = new ManiaAutoGenerator(beatmap).Generate(); Assert.IsTrue(generated.Frames.Count == frame_offset + 4, "Replay must have 4 generated frames"); Assert.AreEqual(1000, generated.Frames[frame_offset].Time, "Incorrect first note hit time"); Assert.AreEqual(3000, generated.Frames[frame_offset + 2].Time, "Incorrect first note release time"); Assert.AreEqual(2000, generated.Frames[frame_offset + 1].Time, "Incorrect second note hit time"); Assert.AreEqual(4000, generated.Frames[frame_offset + 3].Time, "Incorrect second note release time"); Assert.IsTrue(checkContains(generated.Frames[frame_offset], ManiaAction.Key1), "Key1 has not been pressed"); Assert.IsTrue(checkContains(generated.Frames[frame_offset + 1], ManiaAction.Key1, ManiaAction.Key2), "Key1 & Key2 have not been pressed"); Assert.IsFalse(checkContains(generated.Frames[frame_offset + 2], ManiaAction.Key1), "Key1 has not been released"); Assert.IsTrue(checkContains(generated.Frames[frame_offset + 2], ManiaAction.Key2), "Key2 has been released"); Assert.IsFalse(checkContains(generated.Frames[frame_offset + 3], ManiaAction.Key2), "Key2 has not been released"); }
public void TestSingleNoteStair() { // | | | // | | - | // | - | | // | | | var beatmap = new ManiaBeatmap(new StageDefinition { Columns = 2 }); beatmap.HitObjects.Add(new Note { StartTime = 1000 }); beatmap.HitObjects.Add(new Note { StartTime = 2000, Column = 1 }); var generated = new ManiaAutoGenerator(beatmap).Generate(); Assert.IsTrue(generated.Frames.Count == 5, "Replay must have 5 frames"); Assert.AreEqual(1000, generated.Frames[1].Time, "Incorrect first note hit time"); Assert.AreEqual(1000 + ManiaAutoGenerator.RELEASE_DELAY, generated.Frames[2].Time, "Incorrect first note release time"); Assert.AreEqual(2000, generated.Frames[3].Time, "Incorrect second note hit time"); Assert.AreEqual(2000 + ManiaAutoGenerator.RELEASE_DELAY, generated.Frames[4].Time, "Incorrect second note release time"); Assert.IsTrue(checkContains(generated.Frames[1], ManiaAction.Key1), "Key1 has not been pressed"); Assert.IsFalse(checkContains(generated.Frames[2], ManiaAction.Key1), "Key1 has not been released"); Assert.IsTrue(checkContains(generated.Frames[3], ManiaAction.Key2), "Key2 has not been pressed"); Assert.IsFalse(checkContains(generated.Frames[4], ManiaAction.Key2), "Key2 has not been released"); }
public void TestSingleNoteChord() { // | | | // | - | - | // | | | var beatmap = new ManiaBeatmap(new StageDefinition { Columns = 2 }); beatmap.HitObjects.Add(new Note { StartTime = 1000 }); beatmap.HitObjects.Add(new Note { StartTime = 1000, Column = 1 }); var generated = new ManiaAutoGenerator(beatmap).Generate(); Assert.AreEqual(generated.Frames.Count, frame_offset + 2, "Incorrect number of frames"); Assert.AreEqual(1000, generated.Frames[frame_offset].Time, "Incorrect hit time"); Assert.AreEqual(1000 + ManiaAutoGenerator.RELEASE_DELAY, generated.Frames[frame_offset + 1].Time, "Incorrect release time"); Assert.IsTrue(checkContains(generated.Frames[frame_offset], ManiaAction.Key1, ManiaAction.Key2), "Key1 & Key2 have not been pressed"); Assert.IsFalse(checkContains(generated.Frames[frame_offset + 1], ManiaAction.Key1, ManiaAction.Key2), "Key1 & Key2 have not been released"); }
private static ManiaBeatmap createRawBeatmap() { var beatmap = new ManiaBeatmap(new StageDefinition { Columns = 1 }); beatmap.ControlPointInfo.Add(0.0, new TimingControlPoint { BeatLength = 1000 }); // Set BPM to 60 // Add test hit objects beatmap.HitObjects.Add(new Note { StartTime = 4000 }); beatmap.HitObjects.Add(new Note { StartTime = 4500 }); beatmap.HitObjects.Add(new HoldNote { StartTime = 0, EndTime = 125 }); // 1/8 note beatmap.HitObjects.Add(new HoldNote { StartTime = 0, EndTime = 250 }); // 1/4 note beatmap.HitObjects.Add(new HoldNote { StartTime = 0, EndTime = 500 }); // 1/2 note beatmap.HitObjects.Add(new HoldNote { StartTime = 0, EndTime = 1000 }); // 1/1 note beatmap.HitObjects.Add(new HoldNote { StartTime = 0, EndTime = 2000 }); // 2/1 note return(beatmap); }
public EndTimeObjectPatternGenerator(FastRandom random, HitObject hitObject, ManiaBeatmap beatmap, Beatmap originalBeatmap) : base(random, hitObject, beatmap, new Pattern(), originalBeatmap) { var endtimeData = HitObject as IHasEndTime; endTime = endtimeData?.EndTime ?? 0; }
public ManiaAutoGenerator(ManiaBeatmap beatmap) : base(beatmap) { Replay = new Replay { User = new User { Username = @"Autoplay" } }; columnActions = new ManiaAction[Beatmap.TotalColumns]; var normalAction = ManiaAction.Key1; var specialAction = ManiaAction.Special1; int totalCounter = 0; foreach (var stage in Beatmap.Stages) { for (int i = 0; i < stage.Columns; i++) { if (stage.IsSpecialColumn(i)) { columnActions[totalCounter] = specialAction++; } else { columnActions[totalCounter] = normalAction++; } totalCounter++; } } }
public ManiaLegacySkinTransformer(ISkinSource source, IBeatmap beatmap) { this.source = source; this.beatmap = (ManiaBeatmap)beatmap; source.SourceChanged += sourceChanged; sourceChanged(); }
public EndTimeObjectPatternGenerator(FastRandom random, HitObject hitObject, ManiaBeatmap beatmap, Pattern previousPattern, IBeatmap originalBeatmap) : base(random, hitObject, beatmap, previousPattern, originalBeatmap) { endTime = (int)((HitObject as IHasDuration)?.EndTime ?? 0); convertType = PreviousPattern.ColumnWithObjects == TotalColumns ? PatternType.None : PatternType.ForceNotStack; }
private ManiaBeatmap createTestBeatmap() { const double beat_length = 500; var beatmap = new ManiaBeatmap(new StageDefinition { Columns = 1 }) { HitObjects = { new Note { StartTime = 0 }, new Note { StartTime = beat_length / 16 }, new Note { StartTime = beat_length / 12 }, new Note { StartTime = beat_length / 8 }, new Note { StartTime = beat_length / 6 }, new Note { StartTime = beat_length / 4 }, new Note { StartTime = beat_length / 3 }, new Note { StartTime = beat_length / 2 }, new Note { StartTime = beat_length } }, ControlPointInfo = new ControlPointInfo(), BeatmapInfo = { Ruleset = Ruleset.Value }, }; foreach (var note in beatmap.HitObjects) { note.ApplyDefaults(new ControlPointInfo(), new BeatmapDifficulty()); } beatmap.ControlPointInfo.Add(0, new TimingControlPoint { BeatLength = beat_length }); return(beatmap); }
public ManiaLegacySkinTransformer(ISkin skin, IBeatmap beatmap) : base(skin) { this.beatmap = (ManiaBeatmap)beatmap; isLegacySkin = new Lazy <bool>(() => GetConfig <SkinConfiguration.LegacySetting, decimal>(SkinConfiguration.LegacySetting.Version) != null); hasKeyTexture = new Lazy <bool>(() => { string keyImage = this.GetManiaSkinConfig <string>(LegacyManiaSkinConfigurationLookups.KeyImage, 0)?.Value ?? "mania-key1"; return(this.GetAnimation(keyImage, true, true) != null); }); }
public void TestEncodeDecodeSingleStage(params ManiaAction[] actions) { var beatmap = new ManiaBeatmap(new StageDefinition { Columns = 9 }); var frame = new ManiaReplayFrame(0, actions); var legacyFrame = frame.ToLegacy(beatmap); var decodedFrame = new ManiaReplayFrame(); decodedFrame.FromLegacy(legacyFrame, beatmap); Assert.That(decodedFrame.Actions, Is.EquivalentTo(frame.Actions)); }
/// <summary> /// Check whether the column at an overall index (across all stages) is a special column. /// </summary> /// <param name="beatmap">The beatmap.</param> /// <param name="index">The overall index to check.</param> private bool isColumnAtIndexSpecial(ManiaBeatmap beatmap, int index) { foreach (var stage in beatmap.Stages) { if (index >= stage.Columns) { index -= stage.Columns; continue; } return(stage.IsSpecialColumn(index)); } throw new ArgumentException("Column index is too high.", nameof(index)); }
protected PatternGenerator(FastRandom random, HitObject hitObject, ManiaBeatmap beatmap, Pattern previousPattern, IBeatmap originalBeatmap) : base(hitObject, beatmap, previousPattern) { if (random == null) { throw new ArgumentNullException(nameof(random)); } if (originalBeatmap == null) { throw new ArgumentNullException(nameof(originalBeatmap)); } Random = random; OriginalBeatmap = originalBeatmap; RandomStart = TotalColumns == 8 ? 1 : 0; }
/// <summary> /// Find the overall index (across all stages) for a specified special key. /// </summary> /// <param name="maniaBeatmap">The beatmap.</param> /// <param name="specialOffset">The special key offset (0 is S1).</param> /// <returns>The overall index for the special column.</returns> private int getSpecialColumnIndex(ManiaBeatmap maniaBeatmap, int specialOffset) { for (int i = 0; i < maniaBeatmap.TotalColumns; i++) { if (isColumnAtIndexSpecial(maniaBeatmap, i)) { if (specialOffset == 0) { return(i); } specialOffset--; } } throw new ArgumentException("Special key index is too high.", nameof(specialOffset)); }
protected PatternGenerator(HitObject hitObject, ManiaBeatmap beatmap, Pattern previousPattern) { if (hitObject == null) { throw new ArgumentNullException(nameof(hitObject)); } if (beatmap == null) { throw new ArgumentNullException(nameof(beatmap)); } if (previousPattern == null) { throw new ArgumentNullException(nameof(previousPattern)); } HitObject = hitObject; Beatmap = beatmap; PreviousPattern = previousPattern; TotalColumns = Beatmap.TotalColumns; }
public void TestSingleNote() { // | | // | - | // | | var beatmap = new ManiaBeatmap(new StageDefinition { Columns = 1 }); beatmap.HitObjects.Add(new Note { StartTime = 1000 }); var generated = new ManiaAutoGenerator(beatmap).Generate(); Assert.IsTrue(generated.Frames.Count == 3, "Replay must have 3 frames"); Assert.AreEqual(1000, generated.Frames[1].Time, "Incorrect hit time"); Assert.AreEqual(1000 + ManiaAutoGenerator.RELEASE_DELAY, generated.Frames[2].Time, "Incorrect release time"); Assert.IsTrue(checkContains(generated.Frames[1], ManiaAction.Special1), "Special1 has not been pressed"); Assert.IsFalse(checkContains(generated.Frames[2], ManiaAction.Special1), "Special1 has not been released"); }
public void TestSingleHoldNote() { // | | // | * | // | * | // | * | // | | var beatmap = new ManiaBeatmap(new StageDefinition { Columns = 1 }); beatmap.HitObjects.Add(new HoldNote { StartTime = 1000, Duration = 2000 }); var generated = new ManiaAutoGenerator(beatmap).Generate(); Assert.AreEqual(generated.Frames.Count, frame_offset + 2, "Incorrect number of frames"); Assert.AreEqual(1000, generated.Frames[frame_offset].Time, "Incorrect hit time"); Assert.AreEqual(3000, generated.Frames[frame_offset + 1].Time, "Incorrect release time"); Assert.IsTrue(checkContains(generated.Frames[frame_offset], ManiaAction.Special1), "Special1 has not been pressed"); Assert.IsFalse(checkContains(generated.Frames[frame_offset + 1], ManiaAction.Special1), "Special1 has not been released"); }
/// <summary> /// Convert an osu!mania beatmap to a Pulsarc beatmap /// </summary> /// <param name="folder_path">The path to the osu!mania map folder.</param> /// <returns>A list containing all the difficulties as seperate Beatmaps.</returns> public List <Beatmap> Convert(string folder_path) { List <Beatmap> results = new List <Beatmap>(); // See if the provided folder exists if (Directory.Exists(folder_path)) { // Look for .osu files, there should be one for each difficulty foreach (string file in Directory.GetFiles(folder_path, "*.osu")) { Beatmap result = new Beatmap(); ManiaBeatmap maniaBeatmap = new ManiaBeatmap(file); string mapOffset = Config.Get["Converting"]["MapOffset"]; // If the MapOffset value is empty, null, or not an int, set map offset to 0. // Otherwise set it to the provided value. result.MapOffset = string.IsNullOrEmpty(mapOffset) || !int.TryParse(mapOffset, out int a) ? "0" : mapOffset; // Fill in metadata result.FormatVersion = "1"; result.Mapper = maniaBeatmap.Creator; result.Artist = maniaBeatmap.Artist; result.Title = maniaBeatmap.Title; result.Version = maniaBeatmap.Version; result.Audio = maniaBeatmap.AudioFilename; result.PreviewTime = maniaBeatmap.PreviewTime; if (maniaBeatmap.Events.Count > 0) { // Remove the "0,0,"" and "",0,0" on the background line. string backgroundName = maniaBeatmap.Events[0]; string[] charsToRemove = new string[] { ",", "\"", "0" }; foreach (string c in charsToRemove) { backgroundName = backgroundName.Replace(c, ""); } result.Background = backgroundName; } // Look at each HitObject, and assign the appropriate bit to it. foreach (string str in maniaBeatmap.HitObjects) { string[] parts = str.Split(','); int arc = 0; switch (parts[0]) { case "64": arc |= 1 << 2; break; case "192": arc |= 1 << 3; break; case "320": arc |= 1 << 1; break; case "448": arc |= 1 << 0; break; } int time = Int32.Parse(parts[2]) + msOffset; result.Arcs.Add(new Arc(time, arc)); } results.Add(result); } } return(results); }
public HitObjectPatternGenerator(FastRandom random, HitObject hitObject, ManiaBeatmap beatmap, Pattern previousPattern, double previousTime, Vector2 previousPosition, double density, PatternType lastStair, Beatmap originalBeatmap) : base(random, hitObject, beatmap, previousPattern, originalBeatmap) { if (previousTime > hitObject.StartTime) { throw new ArgumentOutOfRangeException(nameof(previousTime)); } if (density < 0) { throw new ArgumentOutOfRangeException(nameof(density)); } StairType = lastStair; TimingControlPoint timingPoint = beatmap.ControlPointInfo.TimingPointAt(hitObject.StartTime); EffectControlPoint effectPoint = beatmap.ControlPointInfo.EffectPointAt(hitObject.StartTime); var positionData = hitObject as IHasPosition; float positionSeparation = ((positionData?.Position ?? Vector2.Zero) - previousPosition).Length; double timeSeparation = hitObject.StartTime - previousTime; if (timeSeparation <= 80) { // More than 187 BPM convertType |= PatternType.ForceNotStack | PatternType.KeepSingle; } else if (timeSeparation <= 95) { // More than 157 BPM convertType |= PatternType.ForceNotStack | PatternType.KeepSingle | lastStair; } else if (timeSeparation <= 105) { // More than 140 BPM convertType |= PatternType.ForceNotStack | PatternType.LowProbability; } else if (timeSeparation <= 125) { // More than 120 BPM convertType |= PatternType.ForceNotStack; } else if (timeSeparation <= 135 && positionSeparation < 20) { // More than 111 BPM stream convertType |= PatternType.Cycle | PatternType.KeepSingle; } else if (timeSeparation <= 150 && positionSeparation < 20) { // More than 100 BPM stream convertType |= PatternType.ForceStack | PatternType.LowProbability; } else if (positionSeparation < 20 && density >= timingPoint.BeatLength / 2.5) { // Low density stream convertType |= PatternType.Reverse | PatternType.LowProbability; } else if (density < timingPoint.BeatLength / 2.5 || effectPoint.KiaiMode) { // High density } else { convertType |= PatternType.LowProbability; } }
public HitObjectPatternGenerator(LegacyRandom random, HitObject hitObject, ManiaBeatmap beatmap, Pattern previousPattern, double previousTime, Vector2 previousPosition, double density, PatternType lastStair, IBeatmap originalBeatmap) : base(random, hitObject, beatmap, previousPattern, originalBeatmap) { StairType = lastStair; TimingControlPoint timingPoint = beatmap.ControlPointInfo.TimingPointAt(hitObject.StartTime); EffectControlPoint effectPoint = beatmap.ControlPointInfo.EffectPointAt(hitObject.StartTime); var positionData = hitObject as IHasPosition; float positionSeparation = ((positionData?.Position ?? Vector2.Zero) - previousPosition).Length; double timeSeparation = hitObject.StartTime - previousTime; if (timeSeparation <= 80) { // More than 187 BPM convertType |= PatternType.ForceNotStack | PatternType.KeepSingle; } else if (timeSeparation <= 95) { // More than 157 BPM convertType |= PatternType.ForceNotStack | PatternType.KeepSingle | lastStair; } else if (timeSeparation <= 105) { // More than 140 BPM convertType |= PatternType.ForceNotStack | PatternType.LowProbability; } else if (timeSeparation <= 125) { // More than 120 BPM convertType |= PatternType.ForceNotStack; } else if (timeSeparation <= 135 && positionSeparation < 20) { // More than 111 BPM stream convertType |= PatternType.Cycle | PatternType.KeepSingle; } else if (timeSeparation <= 150 && positionSeparation < 20) { // More than 100 BPM stream convertType |= PatternType.ForceStack | PatternType.LowProbability; } else if (positionSeparation < 20 && density >= timingPoint.BeatLength / 2.5) { // Low density stream convertType |= PatternType.Reverse | PatternType.LowProbability; } else if (density < timingPoint.BeatLength / 2.5 || effectPoint.KiaiMode) { // High density } else { convertType |= PatternType.LowProbability; } if (!convertType.HasFlagFast(PatternType.KeepSingle)) { if (HitObject.Samples.Any(s => s.Name == HitSampleInfo.HIT_FINISH) && TotalColumns != 8) { convertType |= PatternType.Mirror; } else if (HitObject.Samples.Any(s => s.Name == HitSampleInfo.HIT_CLAP)) { convertType |= PatternType.Gathered; } } }
public DistanceObjectPatternGenerator(FastRandom random, HitObject hitObject, ManiaBeatmap beatmap, Pattern previousPattern, IBeatmap originalBeatmap) : base(random, hitObject, beatmap, previousPattern, originalBeatmap) { convertType = PatternType.None; if (!Beatmap.ControlPointInfo.EffectPointAt(hitObject.StartTime).KiaiMode) { convertType = PatternType.LowProbability; } var distanceData = hitObject as IHasDistance; var repeatsData = hitObject as IHasRepeats; spanCount = repeatsData?.SpanCount() ?? 1; TimingControlPoint timingPoint = beatmap.ControlPointInfo.TimingPointAt(hitObject.StartTime); DifficultyControlPoint difficultyPoint = beatmap.ControlPointInfo.DifficultyPointAt(hitObject.StartTime); // The true distance, accounting for any repeats double distance = (distanceData?.Distance ?? 0) * spanCount; // The velocity of the osu! hit object - calculated as the velocity of a slider double osuVelocity = osu_base_scoring_distance * beatmap.BeatmapInfo.BaseDifficulty.SliderMultiplier * difficultyPoint.SpeedMultiplier / timingPoint.BeatLength; // The duration of the osu! hit object double osuDuration = distance / osuVelocity; EndTime = hitObject.StartTime + osuDuration; SegmentDuration = (EndTime - HitObject.StartTime) / spanCount; }
public EndTimeObjectPatternGenerator(FastRandom random, HitObject hitObject, ManiaBeatmap beatmap, IBeatmap originalBeatmap) : base(random, hitObject, beatmap, new Pattern(), originalBeatmap) { endTime = (HitObject as IHasEndTime)?.EndTime ?? 0; }
protected override void LoadComplete() { const double beat_length = 500; var ruleset = new ManiaRuleset(); var beatmap = new ManiaBeatmap(new StageDefinition { Columns = 1 }) { HitObjects = { new Note { StartTime = 0 }, new Note { StartTime = beat_length / 16 }, new Note { StartTime = beat_length / 12 }, new Note { StartTime = beat_length / 8 }, new Note { StartTime = beat_length / 6 }, new Note { StartTime = beat_length / 4 }, new Note { StartTime = beat_length / 3 }, new Note { StartTime = beat_length / 2 }, new Note { StartTime = beat_length } }, ControlPointInfo = new ControlPointInfo(), BeatmapInfo = { Ruleset = ruleset.RulesetInfo }, }; foreach (var note in beatmap.HitObjects) { note.ApplyDefaults(new ControlPointInfo(), new BeatmapDifficulty()); } beatmap.ControlPointInfo.Add(0, new TimingControlPoint { BeatLength = beat_length }); Child = new Container { Clock = new FramedClock(new ManualClock()), RelativeSizeAxes = Axes.Both, Anchor = Anchor.Centre, Origin = Anchor.Centre, Children = new[] { ruleset.CreateDrawableRulesetWith(beatmap) } }; var config = (ManiaRulesetConfigManager)configCache.GetConfigFor(Ruleset.Value.CreateInstance()); config.BindWith(ManiaRulesetSetting.TimingBasedNoteColouring, configTimingBasedNoteColouring); AddStep("Enable", () => configTimingBasedNoteColouring.Value = true); AddStep("Disable", () => configTimingBasedNoteColouring.Value = false); }
public DistanceObjectPatternGenerator(LegacyRandom random, HitObject hitObject, ManiaBeatmap beatmap, Pattern previousPattern, IBeatmap originalBeatmap) : base(random, hitObject, beatmap, previousPattern, originalBeatmap) { convertType = PatternType.None; if (!Beatmap.ControlPointInfo.EffectPointAt(hitObject.StartTime).KiaiMode) { convertType = PatternType.LowProbability; } var distanceData = hitObject as IHasDistance; var repeatsData = hitObject as IHasRepeats; Debug.Assert(distanceData != null); TimingControlPoint timingPoint = beatmap.ControlPointInfo.TimingPointAt(hitObject.StartTime); DifficultyControlPoint difficultyPoint = hitObject.DifficultyControlPoint; double beatLength; #pragma warning disable 618 if (difficultyPoint is LegacyBeatmapDecoder.LegacyDifficultyControlPoint legacyDifficultyPoint) #pragma warning restore 618 { beatLength = timingPoint.BeatLength * legacyDifficultyPoint.BpmMultiplier; } else { beatLength = timingPoint.BeatLength / difficultyPoint.SliderVelocity; } SpanCount = repeatsData?.SpanCount() ?? 1; StartTime = (int)Math.Round(hitObject.StartTime); // This matches stable's calculation. EndTime = (int)Math.Floor(StartTime + distanceData.Distance * beatLength * SpanCount * 0.01 / beatmap.Difficulty.SliderMultiplier); SegmentDuration = (EndTime - StartTime) / SpanCount; }
public SpecificBeatmapPatternGenerator(FastRandom random, HitObject hitObject, ManiaBeatmap beatmap, Pattern previousPattern, IBeatmap originalBeatmap) : base(random, hitObject, beatmap, previousPattern, originalBeatmap) { }
public static double GetNoteDurationInBeatLength(HoldNote holdNote, ManiaBeatmap beatmap) { double beatLength = beatmap.ControlPointInfo.TimingPointAt(holdNote.StartTime).BeatLength; return(holdNote.Duration / beatLength); }