protected override void Controls()
 {
     if (!Globals.gameSettings.keysModeEnabled)
     {
         if (Input.GetMouseButtonDown(0))
         {
             AddObject();
         }
     }
     else if (MSChartEditorInput.GetInputDown(MSChartEditorInputActions.AddSongObject))
     {
         IList <SyncTrack> searchArray = editor.currentSong.syncTrack;
         int pos = SongObjectHelper.FindObjectPosition(ts, searchArray);
         if (pos == SongObjectHelper.NOTFOUND)
         {
             AddObject();
         }
         else if (searchArray[pos].tick != 0)
         {
             editor.commandStack.Push(new SongEditDelete(searchArray[pos]));
             editor.selectedObjectsManager.currentSelectedObject = null;
         }
     }
 }
示例#2
0
    bool AdjustForAnchors(uint newBpmValue)
    {
        ChartEditor.GetInstance().songObjectPoolManager.SetAllPoolsDirty();

        int pos = SongObjectHelper.FindObjectPosition(currentBPM, currentBPM.song.bpms);

        if (pos != SongObjectHelper.NOTFOUND)
        {
            BPM anchor      = null;
            BPM bpmToAdjust = null;

            int anchorPos = 0;

            // Get the next anchor
            for (int i = pos + 1; i < currentBPM.song.bpms.Count; ++i)
            {
                if (currentBPM.song.bpms[i].anchor != null)
                {
                    anchor    = currentBPM.song.bpms[i];
                    anchorPos = i;
                    // Get the bpm before that anchor
                    bpmToAdjust = currentBPM.song.bpms[i - 1];

                    break;
                }
            }

            if (anchor == null || bpmToAdjust == currentBPM)
            {
                if (currentBPM.value != newBpmValue)
                {
                    ChartEditor.isDirty = true;
                }

                currentBPM.value = newBpmValue;
                return(true);
            }

            // Calculate the minimum the bpm can adjust to
            const float MIN_DT = 0.01f;

            float bpmTime    = (float)anchor.anchor - MIN_DT;
            float resolution = currentBPM.song.resolution;
            // Calculate the time of the 2nd bpm pretending that the adjustable one is super close to the anchor
            for (int i = anchorPos - 1; i > pos + 1; --i)
            {
                // Calculate up until 2 bpms before the anchor
                // Re-hash of the actual time calculation equation in Song.cs
                bpmTime -= (float)TickFunctions.DisToTime(currentBPM.song.bpms[i - 1].tick, currentBPM.song.bpms[i].tick, resolution, currentBPM.song.bpms[i - 1].value / 1000.0f);
            }

            float timeBetweenFirstAndSecond = bpmTime - currentBPM.time;
            // What bpm will result in this exact time difference?
            uint minVal = (uint)(Mathf.Ceil((float)TickFunctions.DisToBpm(currentBPM.song.bpms[pos].tick, currentBPM.song.bpms[pos + 1].tick, timeBetweenFirstAndSecond, currentBPM.song.resolution)) * 1000);

            if (newBpmValue < minVal)
            {
                newBpmValue = minVal;
            }

            if (anchorAdjustment == null)
            {
                anchorAdjustment = bpmToAdjust;
                anchorAdjustmentOriginalValue = new BPM(bpmToAdjust);
            }

            BPM  anchorBPM = anchor;
            uint oldValue  = currentBPM.value;
            currentBPM.value = newBpmValue;

            double deltaTime = (double)anchorBPM.anchor - editor.currentSong.LiveTickToTime(bpmToAdjust.tick, editor.currentSong.resolution);
            uint   newValue  = (uint)Mathf.Round((float)(TickFunctions.DisToBpm(bpmToAdjust.tick, anchorBPM.tick, deltaTime, editor.currentSong.resolution) * 1000.0d));
            currentBPM.value = oldValue;
            if (deltaTime > 0 && newValue > 0)
            {
                if (newValue != 0)
                {
                    bpmToAdjust.value = newValue;
                }
                currentBPM.value = newBpmValue;

                ChartEditor.isDirty = true;
            }
        }
        else
        {
            if (currentBPM.value != newBpmValue)
            {
                ChartEditor.isDirty = true;
            }

            currentBPM.value = newBpmValue;
        }

        return(true);
    }
 public bool IsSelected(SongObject songObject)
 {
     return(SongObjectHelper.FindObjectPosition(songObject, currentSelectedObjects) != SongObjectHelper.NOTFOUND);
 }
    public static SongObject FindObjectToModify(SongObject so)
    {
        ChartEditor editor = ChartEditor.Instance;
        Song        song   = editor.currentSong;
        Chart       chart  = editor.currentChart;

        int index;

        switch ((SongObject.ID)so.classID)
        {
        case SongObject.ID.Note:
            index = SongObjectHelper.FindObjectPosition(so as Note, chart.notes);
            if (index == SongObjectHelper.NOTFOUND)
            {
                return(null);
            }
            return(chart.notes[index]);

        case SongObject.ID.Starpower:
            index = SongObjectHelper.FindObjectPosition(so as Starpower, chart.starPower);
            if (index == SongObjectHelper.NOTFOUND)
            {
                return(null);
            }
            return(chart.starPower[index]);

        case SongObject.ID.ChartEvent:
            index = SongObjectHelper.FindObjectPosition(so as ChartEvent, chart.events);
            if (index == SongObjectHelper.NOTFOUND)
            {
                return(null);
            }
            return(chart.events[index]);

        case SongObject.ID.BPM:
            index = SongObjectHelper.FindObjectPosition(so as BPM, song.bpms);
            if (index == SongObjectHelper.NOTFOUND)
            {
                return(null);
            }
            return(song.bpms[index]);

        case SongObject.ID.TimeSignature:
            index = SongObjectHelper.FindObjectPosition(so as TimeSignature, song.timeSignatures);
            if (index == SongObjectHelper.NOTFOUND)
            {
                return(null);
            }
            return(song.timeSignatures[index]);

        case SongObject.ID.Section:
            index = SongObjectHelper.FindObjectPosition(so as Section, song.sections);
            if (index == SongObjectHelper.NOTFOUND)
            {
                return(null);
            }
            return(song.sections[index]);

        case SongObject.ID.Event:
            index = SongObjectHelper.FindObjectPosition(so as Event, song.events);
            if (index == SongObjectHelper.NOTFOUND)
            {
                return(null);
            }
            return(song.events[index]);

        default:
            Debug.LogError("Object to modify not implemented for object. Object will not be modified.");
            break;
        }

        return(so);
    }
    static MoonscraperEngine.ICommand GenerateCommandsAdjustedForAnchors(BPM currentBPM, uint desiredBpmValue)
    {
        List <SongEditCommand> commands = new List <SongEditCommand>();

        int pos = SongObjectHelper.FindObjectPosition(currentBPM, currentBPM.song.bpms);

        if (pos != SongObjectHelper.NOTFOUND)
        {
            BPM anchor      = null;
            BPM bpmToAdjust = null;

            int anchorPos = 0;

            // Get the next anchor
            for (int i = pos + 1; i < currentBPM.song.bpms.Count; ++i)
            {
                if (currentBPM.song.bpms[i].anchor != null)
                {
                    anchor    = currentBPM.song.bpms[i];
                    anchorPos = i;
                    // Get the bpm before that anchor
                    bpmToAdjust = currentBPM.song.bpms[i - 1];

                    break;
                }
            }

            if (anchor == null || bpmToAdjust == currentBPM)
            {
                commands.Add(new SongEditModify <BPM>(currentBPM, new BPM(currentBPM.tick, desiredBpmValue, currentBPM.anchor)));
                return(new BatchedSongEditCommand(commands));
            }

            // Calculate the minimum the bpm can adjust to
            const float MIN_DT = 0.01f;

            float bpmTime    = (float)anchor.anchor - MIN_DT;
            float resolution = currentBPM.song.resolution;
            // Calculate the time of the 2nd bpm pretending that the adjustable one is super close to the anchor
            for (int i = anchorPos - 1; i > pos + 1; --i)
            {
                // Calculate up until 2 bpms before the anchor
                // Re-hash of the actual time calculation equation in Song.cs
                bpmTime -= (float)TickFunctions.DisToTime(currentBPM.song.bpms[i - 1].tick, currentBPM.song.bpms[i].tick, resolution, currentBPM.song.bpms[i - 1].value / 1000.0f);
            }

            float timeBetweenFirstAndSecond = bpmTime - currentBPM.time;
            // What bpm will result in this exact time difference?
            uint minVal = (uint)(Mathf.Ceil((float)TickFunctions.DisToBpm(currentBPM.song.bpms[pos].tick, currentBPM.song.bpms[pos + 1].tick, timeBetweenFirstAndSecond, currentBPM.song.resolution)) * 1000);

            if (desiredBpmValue < minVal)
            {
                desiredBpmValue = minVal;
            }

            BPM  anchorBPM = anchor;
            uint oldValue  = currentBPM.value;

            ChartEditor editor = ChartEditor.Instance;
            currentBPM.value = desiredBpmValue; // Very much cheating, better to not do this
            double deltaTime = (double)anchorBPM.anchor - editor.currentSong.LiveTickToTime(bpmToAdjust.tick, editor.currentSong.resolution);
            uint   newValue  = (uint)Mathf.Round((float)(TickFunctions.DisToBpm(bpmToAdjust.tick, anchorBPM.tick, deltaTime, editor.currentSong.resolution) * 1000.0d));
            currentBPM.value = oldValue;

            uint finalValue = oldValue;
            if (deltaTime > 0 && newValue > 0)
            {
                if (newValue != 0)
                {
                    commands.Add(new SongEditModify <BPM>(bpmToAdjust, new BPM(bpmToAdjust.tick, newValue, bpmToAdjust.anchor)));
                }

                finalValue = desiredBpmValue;
            }

            desiredBpmValue = finalValue;
        }

        if (desiredBpmValue == currentBPM.value)
        {
            return(null);
        }

        commands.Add(new SongEditModify <BPM>(currentBPM, new BPM(currentBPM.tick, desiredBpmValue, currentBPM.anchor)));
        return(new BatchedSongEditCommand(commands));
    }
示例#6
0
    public void TryFindAndSelectSongObjects(IList <SongObject> songObjects)
    {
        Song  song  = editor.currentSong;
        Chart chart = editor.currentChart;

        foundSongObjects.Clear();

        int warnChartObj = 0;
        int warnSyncObj  = 0;
        int warnEventObj = 0;

        foreach (SongObject so in songObjects)
        {
            ChartObject chartObject = so as ChartObject;
            SyncTrack   syncTrack   = so as SyncTrack;
            Event       eventObject = so as Event;
            if (chartObject != null)
            {
                int insertionIndex = SongObjectHelper.FindObjectPosition(chartObject, chart.chartObjects);
                if (insertionIndex != SongObjectHelper.NOTFOUND)
                {
                    if (!foundSongObjects.Contains(chart.chartObjects[insertionIndex]))
                    {
                        foundSongObjects.Add(chart.chartObjects[insertionIndex]);
                    }
                }
                else
                {
                    ++warnChartObj;
                }
            }
            else if (syncTrack != null)
            {
                int insertionIndex = SongObjectHelper.FindObjectPosition(syncTrack, song.syncTrack);
                if (insertionIndex != SongObjectHelper.NOTFOUND)
                {
                    if (!foundSongObjects.Contains(song.syncTrack[insertionIndex]))
                    {
                        foundSongObjects.Add(song.syncTrack[insertionIndex]);
                    }
                }
                else
                {
                    ++warnSyncObj;
                }
            }
            else if (eventObject != null)
            {
                int insertionIndex = SongObjectHelper.FindObjectPosition(eventObject, song.eventsAndSections);
                if (insertionIndex != SongObjectHelper.NOTFOUND)
                {
                    if (!foundSongObjects.Contains(song.eventsAndSections[insertionIndex]))
                    {
                        foundSongObjects.Add(song.eventsAndSections[insertionIndex]);
                    }
                }
                else
                {
                    ++warnEventObj;
                }
            }
            else
            {
                UnityEngine.Debug.LogError("Unable to handle object " + so.ToString());
            }
        }

        if (warnChartObj > 0)
        {
            UnityEngine.Debug.LogWarning(string.Format("Failed to find {0} chart object/s to highlight", warnChartObj));
        }

        if (warnSyncObj > 0)
        {
            UnityEngine.Debug.LogWarning(string.Format("Failed to find {0} synctrack/s to highlight", warnSyncObj));
        }

        if (warnEventObj > 0)
        {
            UnityEngine.Debug.LogWarning(string.Format("Failed to find {0} event/s to highlight", warnEventObj));
        }

        currentSelectedObjects = foundSongObjects;
        foundSongObjects.Clear();
    }
    void FillNotesKeyboardControlsSustainMode(LaneInfo laneInfo)
    {
        int  laneCount = laneInfo.laneCount;
        bool isTyping  = Services.IsTyping;

        // Tell the system to stop updating the sustain length
        for (int i = 0; i < heldNotes.Length; ++i)
        {
            if (isTyping || Input.GetKeyUp(NumToStringLUT[(i + 1)]))
            {
                ClearHeldNotes(i);
            }
        }

        // Guard to prevent users from pressing keys while dragging out sustains
        if (!GameSettings.extendedSustainsEnabled)
        {
            foreach (Note heldNote in heldNotes)
            {
                if (heldNote != null && heldNote.length > 0)
                {
                    return;
                }
            }
        }

        if (isTyping)
        {
            return;
        }

        bool openNotesBanned, nonOpenNotesBanned;

        CheckBannedInputsForSustainHolds(out openNotesBanned, out nonOpenNotesBanned);
        if (nonOpenNotesBanned)
        {
            return;
        }

        for (int i = 0; i < laneCount + 1; ++i)      // Start at 1 to ignore the multinote
        {
            // Need to make sure the note is at it's correct tick position
            if (Input.GetKeyDown(NumToStringLUT[(i + 1)]))
            {
                int notePos = i;

                if (Input.GetKeyDown(GetOpenNoteInputKey(laneCount)))
                {
                    if (openNotesBanned)     // Ban conflicting inputs as the command stack REALLY doesn't like this.
                    {
                        continue;
                    }

                    notePos = allPlaceableNotes.IndexOf(openNote);
                }

                LeftyFlipReflectionCheck(ref notePos, laneCount);

                allPlaceableNotes[notePos].ExplicitUpdate();
                int pos = SongObjectHelper.FindObjectPosition(allPlaceableNotes[notePos].note, editor.currentChart.notes);

                if (currentPlacementMode == KeysPlacementMode.None)
                {
                    currentPlacementMode = pos == SongObjectHelper.NOTFOUND ? KeysPlacementMode.Adding : KeysPlacementMode.Deleting;
                }

                if (currentPlacementMode == KeysPlacementMode.Adding && pos == SongObjectHelper.NOTFOUND)
                {
                    heldNotes[i]        = allPlaceableNotes[notePos].note.CloneAs <Note>();
                    heldNotes[i].length = 0;
                    currentlyAddingNotes.Add(heldNotes[i]);
                    Debug.Log("Added " + allPlaceableNotes[notePos].note.rawNote + " note at position " + allPlaceableNotes[notePos].note.tick + " using keyboard controls");
                }
                else if (currentPlacementMode == KeysPlacementMode.Deleting)
                {
                    currentlyAddingNotes.Add(editor.currentChart.notes[pos]);
                    Debug.Log("Removed " + editor.currentChart.notes[pos].rawNote + " note at position " + editor.currentChart.notes[pos].tick + " using keyboard controls");
                }
            }
        }
    }
示例#8
0
    void KeyboardControlsSustainMode(LaneInfo laneInfo)
    {
        int  laneCount = laneInfo.laneCount;
        bool isTyping  = Services.IsTyping;

        for (int i = 0; i < heldNotes.Length; ++i)
        {
            // Add in the held note history when user lifts off the keys
            if (isTyping || Input.GetKeyUp((i + 1).ToString()))
            {
                KeySustainActionHistoryInsert(i);
            }
        }

        // Guard to prevent users from pressing keys while dragging out sustains
        if (!GameSettings.extendedSustainsEnabled)
        {
            foreach (Note heldNote in heldNotes)
            {
                if (heldNote != null && heldNote.length > 0)
                {
                    return;
                }
            }
        }

        if (isTyping)
        {
            return;
        }

        for (int i = 0; i < laneCount + 1; ++i)      // Start at 1 to ignore the multinote
        {
            // Need to make sure the note is at it's correct tick position
            if (Input.GetKeyDown((i + 1).ToString()))
            {
                int notePos = i;

                if (Input.GetKeyDown(GetOpenNoteInputKey(laneCount)))
                {
                    notePos = allPlaceableNotes.IndexOf(openNote);
                }

                LeftyFlipReflectionCheck(ref notePos, laneCount);

                allPlaceableNotes[notePos].ExplicitUpdate();
                int pos = SongObjectHelper.FindObjectPosition(allPlaceableNotes[notePos].note, editor.currentChart.notes);

                if (pos == SongObjectHelper.NOTFOUND)
                {
                    Debug.Log("Added " + allPlaceableNotes[notePos].note.rawNote + " note at position " + allPlaceableNotes[notePos].note.tick + " using keyboard controls");
                    heldInitialOverwriteActions[i] = PlaceNote.AddObjectToCurrentChart((Note)allPlaceableNotes[notePos].note.Clone(), editor, out heldNotes[i]);

                    //editor.actionHistory.Insert(PlaceNote.AddObjectToCurrentChart((Note)notes[notePos].note.Clone(), editor, out heldNotes[i - 1]));
                }
                else
                {
                    editor.actionHistory.Insert(new ActionHistory.Delete(editor.currentChart.notes[pos]));
                    Debug.Log("Removed " + editor.currentChart.notes[pos].rawNote + " note at position " + editor.currentChart.notes[pos].tick + " using keyboard controls");
                    editor.currentChart.notes[pos].Delete();
                }
            }
        }
    }