예제 #1
0
        public void ImportColourHaxFromBeatmap(string importPath)
        {
            try {
                var editor  = new BeatmapEditor(importPath);
                var beatmap = editor.Beatmap;

                // Add default colours if there are no colours
                if (beatmap.ComboColours.Count == 0)
                {
                    beatmap.ComboColours.AddRange(ComboColour.GetDefaultComboColours());
                }

                ComboColours.Clear();
                for (int i = 0; i < beatmap.ComboColours.Count; i++)
                {
                    ComboColours.Add(new SpecialColour(beatmap.ComboColours[i].Color, $"Combo{i + 1}"));
                }

                // Remove all colour points since those are getting replaced
                ColourPoints.Clear();

                // Get all the hit objects which can colorhax. AKA new combos and not spinners
                var colorHaxObjects = beatmap.HitObjects.Where(o => o.ActualNewCombo && !o.IsSpinner).ToArray();

                // Get the array with all the lengths of sequences that are going to be checked
                var sequenceLengthChecks = Enumerable.Range(1, ComboColours.Count * 2 + 2).ToArray();

                int   sequenceStartIndex = 0;
                int[] lastNormalSequence = null;
                bool  lastBurst          = false;
                while (sequenceStartIndex < colorHaxObjects.Length)
                {
                    var firstComboHitObject = colorHaxObjects[sequenceStartIndex];

                    var bestSequence = GetBestSequenceAtIndex(
                        sequenceStartIndex,
                        3,
                        colorHaxObjects,
                        beatmap,
                        sequenceLengthChecks,
                        lastBurst,
                        lastNormalSequence
                        )?.Item1;

                    if (bestSequence == null)
                    {
                        lastBurst           = false;
                        sequenceStartIndex += 1;
                        continue;
                    }

                    var bestContribution = GetSequenceContribution(colorHaxObjects, sequenceStartIndex, bestSequence);

                    // Get the colours for every colour index. Using modulo to make sure the index is always in range.
                    var colourSequence = bestSequence.Select(o => ComboColours[MathHelper.Mod(o, ComboColours.Count)]);

                    // Add a new colour point
                    var mode = bestContribution == 1 &&
                               GetComboLength(beatmap.HitObjects, firstComboHitObject) <= MaxBurstLength
                        ? ColourPointMode.Burst
                        : ColourPointMode.Normal;

                    // To optimize on colour points, we dont add a new colour point if the previous point was a burst and
                    // the sequence before the burst is equivalent to this sequence
                    if (!(lastBurst && lastNormalSequence != null && IsSubSequence(bestSequence, lastNormalSequence) &&
                          (bestSequence.Length == lastNormalSequence.Length || bestContribution <= bestSequence.Length)))
                    {
                        ColourPoints.Add(GenerateNewColourPoint(firstComboHitObject.Time, colourSequence, mode));
                    }

                    lastBurst           = mode == ColourPointMode.Burst;
                    sequenceStartIndex += bestContribution;
                    lastNormalSequence  = mode == ColourPointMode.Burst ? lastNormalSequence : bestSequence;
                }
            }
            catch (Exception ex) {
                MessageBox.Show($"{ex.Message}{Environment.NewLine}{ex.StackTrace}", "Error");
            }
        }