예제 #1
0
    // ------------------------------ Private functions ------------------------------


    // Recording

    /// <summary>
    /// Save data of currently one recording chord to the RECORDING-variable (start time, notes, fieldID, sequencer, quantizeOffset).
    /// </summary>
    private void SaveRecordStartData()
    {
        float sequencerPos = (float) CurSequencer.GetSequencerPosition();

        // 1. Start & quantize offset
        if (MusicManager.inst.quantize)
        {
            float quantize = Quantize(sequencerPos);
            recording.start = quantize;

            // hack für sequencerPos bei sequencer.length: quantize 0 oder 32 (sequencer.length)
            if (quantize == 0 && sequencerPos > CurSequencer.length / 2)
            {
                quantize = CurSequencer.length;
            }

            recording.startQuantizeOffset = quantize - sequencerPos;
        }
        else
        {
            recording.start = sequencerPos;
            recording.startQuantizeOffset = 0;
        }

        // 2. End, notes, ID, sequencer
        recording.notes = MusicManager.inst.curChord.DeepCopy().notes;
        recording.fieldID = Player.inst.curField.ID;
        recording.sequencer = CurSequencer;
        recording.isRunning = true;



        // 3. LoopStart object?
        if (!Has1stRecord)
        {
            loopStart = recording.start;
            loopEnd_extended = loopStart + CurSequencer.length;

            var obj = MeshRef.inst.loopObject;
            var parent = MeshRef.inst.recordObj_parent;
            var position = Player.inst.transform.position;

            LoopObject.Create(obj, parent, position, loopStart, loopEnd_extended, loopObjects);
        }
    }
예제 #2
0
    /// <summary>
    /// Write into recording (end-time of the currently played chord), recalculate notes to prevent weird stuff and set notes to sequencer.
    /// </summary>
    private IEnumerator WriteToSequencer_delayed()
    {
        float curPos = (float)CurSequencer.GetSequencerPosition();
        float velocity = MusicManager.inst.velocity;
        var curNotes = MyAudioHelmHelper.GetCurrentNotes(CurSequencer, curPos);
        var doubleNotes = MyAudioHelmHelper.DoubleNotes(recording.notes, curNotes);

        // 1. Write to recording
        // 2. Quantize?
        if (MusicManager.inst.quantize)
        {
            // Legato: quantize recording.end, too
            if (Player.inst.actionState == Player.ActionState.Play)
            {
                float quantize = Quantize(curPos);

                recording.end = quantize;
                recording.endQuantizeOffset = quantize - curPos;

                // Special case: very short notes
                if (recording.end == recording.start)
                {
                    recording.end = (recording.end + MusicManager.inst.quantizeStep) % recording.sequencer.length;
                }
            }
            // Staccato: Dont quantize recording.end
            else
            {
                // get the time the chord was pressed
                recording.end = (curPos + recording.startQuantizeOffset).Modulo(recording.sequencer.length);
                recording.endQuantizeOffset = recording.startQuantizeOffset;
            }
        }
        else
        {
            recording.end = curPos;
        }


        // Special case: recording exceeds self
        if (recording.endExceedsStart)
        {
            recording.end = (recording.start - 0.01f).Modulo(recording.sequencer.length);
            recording.endExceedsStart = false;

            foreach (int note in recording.notes)
            {
                recording.sequencer.NoteOn(note, velocity);
            }
        }



        // 3. IF THERE ARE CURRENTLY EXISTING NOTES: Calc additional notes, to prevent breaking notes
        var usualNotes = new List<NoteContainer>();
        var remainingNotes = new List<NoteContainer>();
        foreach (Note doubleNote in doubleNotes)
        {
            // #1: Existing note within bounds (Sequencer note.start < note.end), curNote plays within sequencer.chord (curNote > start); would disrupt and delete remaining note
            if (recording.end > doubleNote.start && recording.end < doubleNote.end)
            {
                int note = doubleNote.note;
                float start = recording.end + noteAdd; // note add == 0 currently
                float end = doubleNote.end;

                // 1.1. Shorten existing note (1/3)
                if (recording.start != doubleNote.start)    // sonst macht das keinen sinn
                {
                    doubleNote.end = recording.start;
                }

                // Note on
                MusicManager.inst.controller.NoteOn(note, velocity, end - start);

                // 1.2. Add new note for remaining part (== 3/3; recording == 2/3, existing note == 1/3)
                usualNotes.Add(new NoteContainer(note, start, end, velocity));

                //print("existing note, case #1; remaining usual note gets added (3/3)");
            }

            // #2 Existing note extends over the sequencer bounds, would disrupt and stop playing the remaining note
            else if (doubleNote.start > doubleNote.end)
            {
                float oldEnd = doubleNote.end;

                // 2.1. Shorten existing sequencer note
                if (recording.start != doubleNote.start)    // sonst macht das keinen sinn
                {
                    if (recording.start != 0)
                        doubleNote.end = recording.start;
                    else
                        doubleNote.end = recording.sequencer.length - 0.01f;
                }

                // 2.2. Add note for remaining sequencer note?
                //float oldEndPercentage = SequencerPositionPercentage(recording.sequencer, oldEnd, recording.loopStart);
                //float curPosPercentage = SequencerPositionPercentage(recording.sequencer, recording.end, recording.loopStart);
                int note = doubleNote.note;
                float start = recording.end;
                float end = oldEnd;

                var temp = new NoteContainer(note, start, end, velocity);
                remainingNotes.Add(temp); // dont add now because it would be overwritten by usual notes; has to be added at last
                MusicManager.inst.controller.NoteOn(note, velocity, end - start);

                //print("existing note, case #2; remaining undefined note gets added (3/3)");
            }
        }


        var recordCopy = recording.DeepCopy(); // DeepCopy, because otherwise wrong data at later point



        // WAIT to add notes; otherwise notes will disrupt unintendedly
        if (recordCopy.endQuantizeOffset > 0)
        {
            float delay = recordCopy.endQuantizeOffset * LoopData.timePerSixteenth;

            isWaitingToWrite = true;

            yield return new WaitForSeconds(delay);
        }
        isWaitingToWrite = false;



        // #3 Get bridges notes that are NOT being played
        curPos = (float)recordCopy.sequencer.GetSequencerPosition();
        var unplayedBridgeNotes = MyAudioHelmHelper.UnplayedBridgeNotes(CurSequencer, curPos);

        // cur douplicate notes, at the time of the start
        var curNotes_quantize = MyAudioHelmHelper.GetCurrentNotes(recordCopy.sequencer, recordCopy.start);
        var curDoubleNotes_quantize = MyAudioHelmHelper.DoubleNotes(recordCopy.notes, curNotes_quantize);


        // 5. Add remaining usual notes (#1; 3/3)
        foreach (NoteContainer note in usualNotes)
        {
            MyAudioHelmHelper.RemoveIdenticalStartNotes(note, curDoubleNotes_quantize, recordCopy.sequencer);

            recordCopy.sequencer.AddNote(note.note, note.start, note.end, velocity);
        }


        // 4. Write CURRENTLY RECORDED notes
        foreach (int noteNote in recordCopy.notes)
        {
            var note = new Note { note = noteNote, start = recordCopy.start, end = recordCopy.end, velocity = velocity, parent = null };
            //note.parent = null;

            if (note.IsUnplayedBridgeNote(curPos))
            {
                unplayedBridgeNotes.Add(note);
            }
            else
            {
                MyAudioHelmHelper.RemoveIdenticalStartNotes(note, curDoubleNotes_quantize, recordCopy.sequencer);

                // add to sequencer
                recordCopy.sequencer.AddNote(noteNote, recordCopy.start, recordCopy.end, velocity);
            }
        }



        // 5. Add bridge notes again
        foreach (NoteContainer note in remainingNotes) // #2: remaining notes of case #2
        {
            if (note.IsUnplayedBridgeNote(curPos))
            {
                var helmNote = new Note { note = note.note, start = note.start, end = note.end };
                unplayedBridgeNotes.Add(helmNote);
            }
            else
            {
                MyAudioHelmHelper.RemoveIdenticalStartNotes(note, curDoubleNotes_quantize, recordCopy.sequencer);

                recordCopy.sequencer.AddNote(note.note, note.start, note.end, velocity);
            }
        }
        foreach (Note note in unplayedBridgeNotes)  // #3: unplayed bridge notes
        {
            MyAudioHelmHelper.RemoveIdenticalStartNotes(note, curDoubleNotes_quantize, recordCopy.sequencer);

            recordCopy.sequencer.AddNote(note.note, note.start, note.end, velocity);
        }

        yield return null;
        yield return null;
    }