Exemple #1
0
        public void Test_VstEventCollection_CollectionChanged_Replace()
        {
            VstEventCollection target = new VstEventCollection();

            target.Add(new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0));
            target.Add(new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0));

            Assert.AreEqual(2, target.Count, "Collection Count is not as expected.");

            int callCount = 0;

            target.CollectionChanged += (sender, e) =>
            {
                Assert.AreEqual(NotifyCollectionChangedAction.Replace, e.Action, "Unexpected collection changed action.");
                Assert.IsNotNull(e.NewItems, "NewItems collection is null.");
                Assert.AreEqual(1, e.NewItems.Count, "Not the expected number of items in the NewItems collection.");
                Assert.IsNotNull(e.NewItems[0], "NewItems[0] is null.");
                Assert.IsNotNull(e.OldItems, "OldItems collection is null.");
                Assert.AreEqual(1, e.OldItems.Count, "Not the expected number of items in the OldItems collection.");
                Assert.IsNotNull(e.OldItems[0], "OldItems[0] is null.");

                callCount++;
            };

            VstEvent @event = target[0];

            target[0] = target[1];
            target[1] = @event;

            Assert.AreEqual(2, callCount, "Call count is not as expected.");
        }
Exemple #2
0
 /// <summary>
 /// Constructs a new instance.
 /// </summary>
 /// <param name="plugin">Must not be null.</param>
 public MidiProcessor(Plugin plugin)
 {
     _plugin      = plugin;
     Events       = new VstEventCollection();
     NoteOnEvents = new Queue <byte>();
     //InitializeParameters();
 }
Exemple #3
0
 public void Process(VstEventCollection events)
 {
     foreach (var midiMessage in events
              .Where(x => x.EventType == VstEventTypes.MidiEvent)
              .Select(x => new MidiMessage((VstMidiEvent)x)))
     {
         if (midiMessage.HasStatusByte((byte)MidiChannelCommand.NoteOff))
         {
             NoteOff(GetNoteEventArgsFromMessage(midiMessage));
         }
         else if (midiMessage.HasStatusByte((byte)MidiChannelCommand.NoteOn))
         {
             if (midiMessage.Data2 == 0) // Velocity
             {
                 NoteOff(GetNoteEventArgsFromMessage(midiMessage));
             }
             else
             {
                 NoteOn(GetNoteEventArgsFromMessage(midiMessage));
             }
         }
         else if (midiMessage.HasStatusByte((byte)MidiChannelCommand.ControlChange))
         {
             if (midiMessage.Data1 == (byte)MidiControllerType.AllNotesOff ||
                 midiMessage.Data1 == (byte)MidiControllerType.AllSoundOff)
             {
                 var notes = new HashSet <int>(_pressedNotes);
                 foreach (var pressedNote in notes)
                 {
                     NoteOff(new NoteEventArgs(pressedNote, 0));
                 }
             }
         }
     }
 }
Exemple #4
0
        /// <summary>
        /// Handles and filters the incoming midi events.
        /// </summary>
        /// <param name="events">The midi events for the current cycle.</param>
        public void Process(VstEventCollection events)
        {
            foreach (VstEvent evnt in events)
            {
                if (evnt.EventType == VstEventTypes.MidiEvent)
                {
                    VstMidiEvent midiEvent = (VstMidiEvent)evnt;

                    //System.Diagnostics.Debug.WriteLine("Receiving Midi Event:" + midiEvent.MidiData[0], "VST.NET");

                    // pass note on and note off to the sample manager

                    if ((midiEvent.Data[0] & 0xF0) == 0x80)
                    {
                        _plugin.SampleManager.ProcessNoteOffEvent(midiEvent.Data[1]);
                    }

                    if ((midiEvent.Data[0] & 0xF0) == 0x90)
                    {
                        // note on with velocity = 0 is a note off
                        if (midiEvent.Data[2] == 0)
                        {
                            _plugin.SampleManager.ProcessNoteOffEvent(midiEvent.Data[1]);
                        }
                        else
                        {
                            _plugin.SampleManager.ProcessNoteOnEvent(midiEvent.Data[1]);
                        }
                    }
                }
            }
        }
        public void Test_VstEventCollection_CollectionChanged_Replace()
        {
            var target = new VstEventCollection
            {
                new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0),
                new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0)
            };

            target.Should().HaveCount(2);

            int callCount = 0;

            target.CollectionChanged += (sender, e) =>
            {
                e.Action.Should().Be(NotifyCollectionChangedAction.Replace);
                e.NewItems.Should().NotBeNullOrEmpty();
                e.NewItems[0].Should().NotBeNull();
                e.OldItems.Should().NotBeNullOrEmpty();
                e.OldItems[0].Should().NotBeNull();

                callCount++;
            };

            VstEvent @event = target[0];

            target[0] = target[1];
            target[1] = @event;

            callCount.Should().Be(2);
        }
Exemple #6
0
        /// <summary>
        /// Handles and filters the incoming midi events.
        /// </summary>
        /// <param name="events">The midi events for the current cycle.</param>
        public void Process(VstEventCollection events)
        {
            foreach (VstEvent evnt in events)
            {
                if (evnt.EventType == VstEventTypes.MidiEvent)
                {
                    VstMidiEvent midiEvent = (VstMidiEvent)evnt;

                    // pass note on and note off to the sample manager
                    if ((midiEvent.Data[0] & 0xF0) == 0x80)
                    {
                        _plugin.SampleManager.ProcessNoteOffEvent(midiEvent.Data[1]);
                    }

                    if ((midiEvent.Data[0] & 0xF0) == 0x90)
                    {
                        // note on with velocity = 0 is a note off
                        if (midiEvent.Data[2] == 0)
                        {
                            _plugin.SampleManager.ProcessNoteOffEvent(midiEvent.Data[1]);
                        }
                        else
                        {
                            _plugin.SampleManager.ProcessNoteOnEvent(midiEvent.Data[1]);
                        }
                    }
                }
            }
        }
Exemple #7
0
 /// <summary>
 /// Constructs a new instance.
 /// </summary>
 /// <param name="plugin">Must not be null.</param>
 public MidiProcessor(Plugin plugin)
 {
     _plugin      = plugin;
     Events       = new VstEventCollection();
     NoteOnEvents = new Queue <byte>();
     _timeInfo    = new VstTimeInfo();
 }
        /// <summary>
        ///     Midi events are received from the host on this method and are either send to the DryMssEventRelay or
        ///     stored internally.
        /// </summary>
        /// <param name="events">A collection with midi events. Never null.</param>
        /// <remarks>
        ///     Note that some hosts will only receieve midi events during audio processing.
        ///     See also <see cref="IVstPluginAudioProcessor"/>.
        /// </remarks>
        public void Process(VstEventCollection vstEvents)
        {
            if (vstEvents == null || vstEvents.Count == 0 || this.vstHost == null)
            {
                return;
            }

            // NOTE: other types of events could be in the collection!
            foreach (VstEvent evnt in vstEvents)
            {
                if (evnt.EventType == VstEventTypes.MidiEvent)
                {
                    VstMidiEvent midiEvent = (VstMidiEvent)evnt;
                    MssEvent     mssEvent  = ConvertVstMidiEventToMssEvent(midiEvent,
                                                                           this.SampleTimeAtStartOfProcessingCycle,
                                                                           this.hostInfoOutputPort.SampleRate);

                    if (mssEvent == null)
                    {
                        outEvents.Add(evnt);
                    }
                    else
                    {
                        this.dryMssEventInputPort.ReceiveDryMssEvent(mssEvent);
                    }
                }
                else
                {
                    // non VstMidiEvent
                    outEvents.Add(evnt);
                }
            }
        }
        public void Process_NoteOn_SentToRelay()
        {
            VstEventCollection vstEvents = new VstEventCollection();

            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.NoteOn)));

            Test_Process_VstEventCollection_SentToReplay(vstEvents, 1);
        }
        protected void Test_Process_VstEventCollection_SentToReplay(VstEventCollection vstEvents, int NumMssCompatibleEvents)
        {
            MidiHandlerProtectedWrapper midiHandler = Factory_MidiHandler_Basic();

            midiHandler.Process(vstEvents);

            Assert.AreEqual(numDryEventsReceivedByRelay, NumMssCompatibleEvents);
        }
 /// <summary>
 /// Midi events are received from the host on this method.
 /// </summary>
 /// <param name="events">A collection with midi events. Never null.</param>
 /// <remarks>
 /// Note that some hosts will only receieve midi events during audio processing.
 /// See also <see cref="IVstPluginAudioProcessor"/>.
 /// </remarks>
 public void Process(VstEventCollection events)
 {
     CurrentEvents = events;
     //_plugin.PluginEditor.Log("Midi Process");
     if (!SyncWithAudioProcessor)
     {
         ProcessCurrentEvents();
     }
 }
Exemple #12
0
        /// <summary>
        /// Midi events are received from the host on this method.
        /// </summary>
        /// <param name="events">A collection with midi events. Never null.</param>
        /// <remarks>
        /// Note that some hosts will only receieve midi events during audio processing.
        /// See also <see cref="IVstPluginAudioProcessor"/>.
        /// </remarks>
        public void Process(VstEventCollection events)
        {
            CurrentEvents = events;

            if (!SyncWithAudioProcessor)
            {
                ProcessCurrentEvents();
            }
        }
        public void Process_SysExEvent_NothingSentToRelay()
        {
            VstEventCollection vstEvents        = new VstEventCollection();
            VstMidiSysExEvent  unsupportedEvent = new VstMidiSysExEvent(0, new byte[3]);

            vstEvents.Add(unsupportedEvent);

            Test_Process_VstEventCollection_SentToReplay(vstEvents, 0);
        }
Exemple #14
0
        public void Process(VstEventCollection events)
        {
            int _transposeSemitones = _plugin.Transpose.Semitones;

            foreach (VstEvent anyEvent in events)
            {
                if (anyEvent.EventType != VstEventTypes.MidiEvent)
                {
                    continue;
                }

                VstMidiEvent midiEvent = (VstMidiEvent)anyEvent;


                if (((midiEvent.Data[0] & 0xF0) == 0x80 || (midiEvent.Data[0] & 0xF0) == 0x90))
                {   // these are all the note on and note off events.
                    if (_transposeSemitones != 0)
                    {
                        VstMidiEvent mappedEvent = null;
                        byte[]       midiData    = new byte[4];
                        midiData[0] = midiEvent.Data[0];
                        int _note = midiEvent.Data[1] + _transposeSemitones;
                        if (_note < 0 || _note > 127)
                        {
                            continue;                           // skip out of range notes.
                        }
                        midiData[1] = (byte)_note;
                        midiData[2] = midiEvent.Data[2];
                        mappedEvent = new VstMidiEvent(midiEvent.DeltaFrames,
                                                       midiEvent.NoteLength,
                                                       midiEvent.NoteOffset,
                                                       midiData,
                                                       midiEvent.Detune,
                                                       midiEvent.NoteOffVelocity);
                        Events.Add(mappedEvent);
                        // add raw note-on note numbers to the queue
                        if ((midiEvent.Data[0] & 0xF0) == 0x90)
                        {
                            lock (((ICollection)NoteOnEvents).SyncRoot)
                            {
                                NoteOnEvents.Enqueue(midiEvent.Data[1]);
                            }
                        }
                    }
                    else
                    {   // we're not transposing, so just pass it through.
                        Events.Add(anyEvent);
                    }
                }
                else
                {   // not a midi on-off event, so pass it through.
                    Events.Add(anyEvent);
                }
            }
        }
        public void Test_VstEventCollection_Constructor()
        {
            var target = new VstEventCollection();

            target.IsReadOnly.Should().BeFalse();

            target.Add(new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0));
            target.Add(new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0));
            target.Should().HaveCount(2);

            target.Clear();
            target.Should().BeEmpty();
        }
        public void Process_MultipleMsgTypes_SentToRelay()
        {
            VstEventCollection vstEvents = new VstEventCollection();

            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.NoteOn)));
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.NoteOff)));
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.CC)));
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.ChanAftertouch)));
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.PitchBend)));
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.PolyAftertouch)));

            Test_Process_VstEventCollection_SentToReplay(vstEvents, 6);
        }
Exemple #17
0
        public void Process(VstEventCollection events)
        {
            foreach (VstEvent evnt in events)
            {
                if (evnt.EventType != VstEventTypes.MidiEvent)
                {
                    continue;
                }

                var midiEvent = (VstMidiEvent)evnt;

                if (((midiEvent.Data[0] & 0xF0) == 0x80 || (midiEvent.Data[0] & 0xF0) == 0x90))
                {
                    if (_noteMap.Contains(midiEvent.Data[1]))
                    {
                        byte[] midiData = new byte[4];
                        midiData[0] = midiEvent.Data[0];
                        midiData[1] = _noteMap[midiEvent.Data[1]].OutputNoteNumber;
                        midiData[2] = midiEvent.Data[2];

                        var mappedEvent = new VstMidiEvent(midiEvent.DeltaFrames,
                                                           midiEvent.NoteLength,
                                                           midiEvent.NoteOffset,
                                                           midiData,
                                                           midiEvent.Detune,
                                                           midiEvent.NoteOffVelocity);

                        Events.Add(mappedEvent);

                        // add raw note-on note numbers to the queue
                        if ((midiEvent.Data[0] & 0xF0) == 0x90)
                        {
                            lock (((ICollection)NoteOnEvents).SyncRoot)
                            {
                                NoteOnEvents.Enqueue(midiEvent.Data[1]);
                            }
                        }
                    }
                    else if (MidiThru)
                    {
                        // add original note event
                        Events.Add(evnt);
                    }
                }
                else if (MidiThru)
                {
                    // add original (non-note) event
                    Events.Add(evnt);
                }
            }
        }
Exemple #18
0
        public void Test_VstEventCollection_ReadOnlyConstructor()
        {
            VstEvent[] events = new VstEvent[2];
            events[0] = new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0);
            events[1] = new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0);

            VstEventCollection target = new VstEventCollection(events);

            Assert.AreEqual(events.Length, target.Count, "Count does not match.");
            Assert.AreEqual(2, target.Count, "Count is not as expected.");
            Assert.IsTrue(target.IsReadOnly, "Collection is not read-only.");
            Assert.AreEqual(events[0], target[0], "First item does not match.");
            Assert.AreEqual(events[1], target[1], "Second item does not match.");
        }
Exemple #19
0
        public void Test_VstEventCollection_Constructor()
        {
            VstEventCollection target = new VstEventCollection();

            Assert.IsFalse(target.IsReadOnly, "Collection is read-only.");

            target.Add(new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0));
            target.Add(new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0));

            Assert.AreEqual(2, target.Count, "Count is not as expected.");

            target.Clear();
            Assert.AreEqual(0, target.Count, "Count is not zero.");
        }
        public void Test_VstEventCollection_ReadOnlyConstructor()
        {
            var events = new VstEvent[2];

            events[0] = new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0);
            events[1] = new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0);

            var target = new VstEventCollection(events);

            target.Should().HaveCount(events.Length);
            target.IsReadOnly.Should().BeTrue();
            target[0].Should().Be(events[0]);
            target[1].Should().Be(events[1]);
        }
        public void ProcessCurrentEvents()
        {
            //_plugin.PluginEditor.Log("ProcessCurrentEvents");

            // a plugin must implement IVstPluginMidiSource or this call will throw an exception.
            var midiHost = _plugin.Host.GetInstance <IVstMidiProcessor>();

            // always expect some hosts not to support this.
            if (midiHost != null)
            {
                var outEvents = new VstEventCollection();

                var someCommands = _plugin.Host.GetInstance <IVstHostCommands20>();
                var timeInfo     = someCommands.GetTimeInfo(
                    VstTimeInfoFlags.PpqPositionValid | VstTimeInfoFlags.BarStartPositionValid | VstTimeInfoFlags.TempoValid);
                if (CurrentEvents != null)
                {
                    // NOTE: other types of events could be in the collection!
                    foreach (VstEvent evnt in CurrentEvents)
                    {
                        switch (evnt.EventType)
                        {
                        case VstEventTypes.MidiEvent:
                            var midiEvent = (VstMidiEvent)evnt;

                            midiEvent = Cascade.ProcessEvent(midiEvent, timeInfo);

                            //_plugin.PluginEditor.Log("tempo" + x.Tempo);

                            outEvents.Add(midiEvent);
                            break;

                        default:
                            // non VstMidiEvent
                            outEvents.Add(evnt);
                            break;
                        }
                    }
                }

                outEvents.AddRange(Cascade.CreateNotes(timeInfo));

                midiHost.Process(outEvents);
            }

            // Clear the cache, we've processed the events.
            CurrentEvents = null;
        }
        public void Process_SomeSupportedSomeUnsupporedEvents_SomeSentToRelay()
        {
            VstEventCollection vstEvents = new VstEventCollection();

            //Supported event type
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.PitchBend)));

            //Unsupported event type
            VstMidiSysExEvent unsupportedEvent = new VstMidiSysExEvent(0, new byte[3]);

            vstEvents.Add(unsupportedEvent);

            //Supported event type
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.PolyAftertouch)));

            Test_Process_VstEventCollection_SentToReplay(vstEvents, 2);
        }
Exemple #23
0
        public void ProcessCurrentEvents()
        {
            if (CurrentEvents == null || CurrentEvents.Count == 0) return;

            // a plugin must implement IVstPluginMidiSource or this call will throw an exception.
            IVstMidiProcessor midiHost = _plugin.Host.GetInstance<IVstMidiProcessor>();

            // always expect some hosts not to support this.
            if (midiHost != null)
            {
                VstEventCollection outEvents = new VstEventCollection();

                // NOTE: other types of events could be in the collection!
                foreach (VstEvent evnt in CurrentEvents)
                {
                    if (evnt.EventType == VstEventTypes.MidiEvent)
                    {
                        VstMidiEvent midiEvent = (VstMidiEvent)evnt;
                        if ((midiEvent.Data[0] & 0xF0) == 0x80)
                        {
                            _plugin._synth.ProcessNoteOffEvent(midiEvent.Data[1]);
                        }
                        if ((midiEvent.Data[0] & 0xF0) == 0x90)
                        {
                            // note on with velocity = 0 is a note off
                            if (midiEvent.Data[2] == 0)
                            {
                                _plugin._synth.ProcessNoteOffEvent(midiEvent.Data[1]);
                            }
                            else
                            {
                                //midiEvent = _gain.ProcessEvent(midiEvent);
                                //midiEvent = _transpose.ProcessEvent(midiEvent);
                                _plugin._synth.ProcessNoteOnEvent(midiEvent.Data[1]);
                            }
                        }
                    }
                    else
                    {
                        // non VstMidiEvent
                        outEvents.Add(evnt);
                    }
                }
                //midiHost.Process(outEvents);
            }
        }
        public void Test_VstEventCollection_CollectionChanged_Add()
        {
            var target    = new VstEventCollection();
            int callCount = 0;

            target.CollectionChanged += (sender, e) =>
            {
                e.Action.Should().Be(NotifyCollectionChangedAction.Add);
                e.NewItems.Should().NotBeNullOrEmpty();
                e.NewItems[0].Should().NotBeNull();

                callCount++;
            };

            target.Add(new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0));
            target.Add(new VstMidiEvent(0, 100, 0, new byte[] { 100, 110, 120 }, 0, 0));

            callCount.Should().Be(2);
        }
Exemple #25
0
        public void ProcessCurrentEvents()
        {
            if (CurrentEvents == null || CurrentEvents.Count == 0)
            {
                return;
            }

            // a plugin must implement IVstPluginMidiSource or this call will throw an exception.
            IVstMidiProcessor midiHost = _plugin.Host.GetInstance <IVstMidiProcessor>();

            // always expect some hosts not to support this.
            if (midiHost != null)
            {
                VstEventCollection outEvents = new VstEventCollection();

                // NOTE: other types of events could be in the collection!
                foreach (VstEvent evnt in CurrentEvents)
                {
                    switch (evnt.EventType)
                    {
                    case VstEventTypes.MidiEvent:
                        VstMidiEvent midiEvent = (VstMidiEvent)evnt;

                        midiEvent = Gain.ProcessEvent(midiEvent);
                        midiEvent = Transpose.ProcessEvent(midiEvent);

                        outEvents.Add(midiEvent);
                        break;

                    default:
                        // non VstMidiEvent
                        outEvents.Add(evnt);
                        break;
                    }
                }

                midiHost.Process(outEvents);
            }

            // Clear the cache, we've processed the events.
            CurrentEvents = null;
        }
Exemple #26
0
        public MidiProcessor(Plugin plugin)
        {
            _plugin        = plugin;
            Events         = new VstEventCollection();
            NoteOnNumbers  = new Queue <byte>();
            NoteOffNumbers = new Queue <byte>();
            _noteOnEvents  = new List <VstMidiEvent>();
            _octavesAddedOrderedNoteOnEvents = new List <VstMidiEvent>();
            _rythm           = new List <NoteLengthFrames>();
            Probability      = 100;
            NoteLengthsArray = new NoteLengths[4];
            AccentsArray     = new Accents[4];

            for (int i = 0; i < 4; i++)
            {
                NoteLengthsArray[i] = NoteLengths.quarter;
                AccentsArray[i]     = Accents.none;
            }

            CountRythm();
        }
        /// <summary>
        /// Removes notes that are expired and generates new notes.
        /// </summary>
        /// <param name="events"></param>
        public void Process(VstEventCollection events)
        {
            // remove notes that are expired
            RemoveNotesThatAreExpired();

            // check if time since last tick is larger than the speed of the board
            if ((DateTime.Now - lastTick).Milliseconds > _plugin.BoardSettings.Speed)
            {
                // advance the board to its next state
                _plugin.BoardSettings.Board.NextState();

                // add notes to play based on the active cells
                AddNotesToPlay(_plugin.BoardSettings);

                // let the editor know to update the board
                var _uiEditor = _plugin.GetInstance <PluginEditor>();
                _uiEditor.UpdateBoard();

                lastTick = DateTime.Now;
            }
        }
Exemple #28
0
        public void ProcessCurrentEvents()
        {
            if (CurrentEvents == null || CurrentEvents.Count == 0)
            {
                return;
            }

            // always expect some hosts not to support this.
            if (_midiHost != null)
            {
                VstEventCollection outEvents = new VstEventCollection();

                // NOTE: other types of events could be in the collection!
                foreach (VstEvent evnt in CurrentEvents)
                {
                    switch (evnt.EventType)
                    {
                    case VstEventTypes.MidiEvent:
                        VstMidiEvent midiEvent = (VstMidiEvent)evnt;

                        midiEvent = Gain.ProcessEvent(midiEvent);
                        midiEvent = Transpose.ProcessEvent(midiEvent);

                        outEvents.Add(midiEvent);
                        break;

                    default:
                        // non VstMidiEvent
                        outEvents.Add(evnt);
                        break;
                    }
                }

                _midiHost.Process(outEvents);
            }

            // Clear the cache, we've processed the events.
            CurrentEvents = null;
        }
        /// <summary>
        /// Обработка новых входных данных.
        /// </summary>
        /// <param name="events"></param>
        public void Process(VstEventCollection events)
        {
            foreach (var e in events)
            {
                if (e.EventType == VstEventTypes.MidiEvent)
                {
                    var  midiEvent = (VstMidiEvent)e;
                    byte firstByte = midiEvent.Data[0];

                    if (0x80 <= firstByte && firstByte < 0x90) // Note off
                    {
                        pressedNotesCount -= 1;
                        OnNoteOff(midiEvent.Data[1], midiEvent.Data[2]);
                    }

                    else if (0x90 <= firstByte && firstByte < 0xA0) // Note on
                    {
                        pressedNotesCount += 1;
                        OnNoteOn(midiEvent.Data[1], midiEvent.Data[2]);
                    }
                }
            }
        }
        /// <summary>
        /// Passes the <paramref name="events"/> onto the host.
        /// </summary>
        /// <param name="events">Must not be null.</param>
        /// <exception cref="System.ArgumentNullException">Thrown when <paramref name="events"/> is not set to an instance of an object.</exception>
        public void Process(VstEventCollection events)
        {
            Throw.IfArgumentIsNull(events, nameof(events));

            _host.HostCommandProxy.Commands.ProcessEvents(events.ToArray());
        }
 /// <summary>
 /// Constructs a new instance.
 /// </summary>
 /// <param name="plugin">Must not be null.</param>
 public MidiProcessor(Plugin plugin)
 {
     _plugin = plugin;
     Events = new VstEventCollection();
 }
        // Process the incoming VST events.  *** This is the core of the VST right here. ***
        public void Process(VstEventCollection inputEvents)
        {
            if (_plugin == null) return;

            _plugin.callCount++;

            bool thrudone = false;

            foreach (VstEvent evnt in inputEvents)
            {
                _plugin.eventCount++;

                // Skip non-MIDI Events
                if (evnt.EventType != VstEventTypes.MidiEvent)
                {
                    continue;
                }

                _plugin.midiCount++;

                // If set in options, keep the original event as well
                if (_plugin.Options.MidiThruAll)
                {
                    Events.Add(evnt);
                    thrudone = true;
                }

                // Don't do any more if we aren't running.
                if (_plugin.CurrentMode != Constants.Modes.RUN) continue;

                // Construct a MIDI event and act on it
                VstMidiEvent midiInputEvent = (VstMidiEvent)evnt;
                byte command = (byte)(midiInputEvent.Data[0] & 0xF0);
                byte channel = (byte)(midiInputEvent.Data[0] & 0x0F);
                byte note = midiInputEvent.Data[1];
                byte velocity = midiInputEvent.Data[2];

                MapNoteItem map = _plugin.NoteMaps[note];
                byte[] midiData = null;

                // Filter out everything except Note On/Note Off and CC events
                switch (command)
                {
                    case 0x90: // Note On
                        map.Triggered(Constants.MapTypes.ON);

                        if (map.isDefined(Constants.MapTypes.ON))
                        {
                            _plugin.hitCount++;
                            midiData = MapNoteItem.StringToBytes(map.OutputBytesStringOn, channel, velocity);
                        }
                        break;

                    case 0x80: // Note Off
                        map.Triggered(Constants.MapTypes.OFF);

                        if (map.isDefined(Constants.MapTypes.OFF))
                        {
                            _plugin.hitCount++;
                            midiData = MapNoteItem.StringToBytes(map.OutputBytesStringOff, channel, velocity);
                        }
                        break;

                    case 0xB0: // Continuous Controller
                        map.Triggered(Constants.MapTypes.CC);

                        if (map.isDefined(Constants.MapTypes.CC))
                        {
                            _plugin.hitCount++;
                            midiData = MapNoteItem.StringToBytes(map.OutputBytesStringCC, channel, velocity);
                        }
                        break;

                    default:
                        // Ignore everything else, but keep going below
                        break;
                }

                // Check that we got a result.  If not - no match.
                if (midiData == null)
                {
                    if (_plugin.Options.MidiThru)
                    {
                        // add original event, if not added already.
                        if (!thrudone)
                        {
                            Events.Add(evnt);
                        }
                    }
                    continue;
                }

                // In most cases, use VstMidiSysExEvent in place of VstMidiEvent, since this seems to allow arbitary bytes.
                if (_plugin.Options.AlwaysSysEx)
                {
                    VstMidiSysExEvent mappedEvent = new VstMidiSysExEvent(midiInputEvent.DeltaFrames, midiData);
                    Events.Add(mappedEvent);
                }
                else  // Ugly!  Split message into three-byte chunks and send them all.
                {
                    List<byte[]> midichunks = new List<byte[]>();

                    for (int i = 0; i < midiData.Length; i += 3)
                    {
                        midichunks.Add(midiData.Skip(i).Take(3).ToArray());
                    }

                    foreach (byte[] midi in midichunks)
                    {
                        VstMidiEvent mappedEvent = new VstMidiEvent(midiInputEvent.DeltaFrames, midiInputEvent.NoteLength, midiInputEvent.NoteOffset, midi, midiInputEvent.Detune, midiInputEvent.NoteOffVelocity);
                        Events.Add(mappedEvent);
                    }
                }
            } // foreach
        }
        protected void Test_Process_VstEventCollection_SentToReplay(VstEventCollection vstEvents, int NumMssCompatibleEvents)
        {
            MidiHandlerProtectedWrapper midiHandler = Factory_MidiHandler_Basic();
            midiHandler.Process(vstEvents);

            Assert.AreEqual(numDryEventsReceivedByRelay, NumMssCompatibleEvents);
        }
        public void Process_SysExEvent_NothingSentToRelay()
        {
            VstEventCollection vstEvents = new VstEventCollection();
            VstMidiSysExEvent unsupportedEvent = new VstMidiSysExEvent(0, new byte[3]);
            vstEvents.Add(unsupportedEvent);

            Test_Process_VstEventCollection_SentToReplay(vstEvents, 0);
        }
        public void Process_SomeSupportedSomeUnsupporedEvents_SomeSentToRelay()
        {
            VstEventCollection vstEvents = new VstEventCollection();

            //Supported event type
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.PitchBend)));

            //Unsupported event type
            VstMidiSysExEvent unsupportedEvent = new VstMidiSysExEvent(0, new byte[3]);
            vstEvents.Add(unsupportedEvent);

            //Supported event type
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.PolyAftertouch)));

            Test_Process_VstEventCollection_SentToReplay(vstEvents, 2);
        }
        public void Process_NoteOn_SentToRelay()
        {
            VstEventCollection vstEvents = new VstEventCollection();
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.NoteOn)));

            Test_Process_VstEventCollection_SentToReplay(vstEvents, 1);
        }
        public void Process_MultipleMsgTypes_SentToRelay()
        {
            VstEventCollection vstEvents = new VstEventCollection();
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.NoteOn)));
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.NoteOff)));
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.CC)));
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.ChanAftertouch)));
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.PitchBend)));
            vstEvents.Add(Factory_VstMidiEvent_Basic(0, CreateMidiDataWithDefaultValues(MssMsgType.PolyAftertouch)));

            Test_Process_VstEventCollection_SentToReplay(vstEvents, 6);
        }
Exemple #38
0
 /// <summary>
 /// Midi events are received from the host on this method.
 /// </summary>
 /// <param name="events">A collection with midi events. Never null.</param>
 /// <remarks>
 /// Note that some hosts will only receieve midi events during audio processing.
 /// See also <see cref="IVstPluginAudioProcessor"/>.
 /// </remarks>
 public void Process(VstEventCollection events)
 {
     CurrentEvents = events;
     ProcessCurrentEvents();
 }
        /// <summary>
        ///     Midi events are received from the host on this method and are either send to the DryMssEventRelay or 
        ///     stored internally.
        /// </summary>
        /// <param name="events">A collection with midi events. Never null.</param>
        /// <remarks>
        ///     Note that some hosts will only receieve midi events during audio processing.
        ///     See also <see cref="IVstPluginAudioProcessor"/>.
        /// </remarks>
        public void Process(VstEventCollection vstEvents)
        {
            if (vstEvents == null || vstEvents.Count == 0 || this.vstHost == null) return;

            // NOTE: other types of events could be in the collection!
            foreach (VstEvent evnt in vstEvents)
            {
                if (evnt.EventType == VstEventTypes.MidiEvent)
                {
                    VstMidiEvent midiEvent = (VstMidiEvent)evnt;
                    MssEvent mssEvent = ConvertVstMidiEventToMssEvent(midiEvent,
                                                                      this.SampleTimeAtStartOfProcessingCycle,
                                                                      this.hostInfoOutputPort.SampleRate);

                    if (mssEvent == null)
                    {
                        outEvents.Add(evnt);
                    }
                    else
                    {
                        this.dryMssEventInputPort.ReceiveDryMssEvent(mssEvent);
                    }
                }
                else
                {
                    // non VstMidiEvent
                    outEvents.Add(evnt);
                }
            }
        }
Exemple #40
0
        // Process the incoming VST events.  This is the core of the app right here.  !!!!
        public void Process(VstEventCollection inputEvents)
        {
            _plugin.callCount++;

            foreach (VstEvent evnt in inputEvents)
            {
                _plugin.eventCount++;

                // Skip non-MIDI Events
                if (evnt.EventType != VstEventTypes.MidiEvent)
                {
                    continue;
                }

                _plugin.midiCount++;

                VstMidiEvent midiInputEvent = (VstMidiEvent)evnt;

                // Filter out everything except Note On/Note Off events
                byte midiCommand = (byte)(midiInputEvent.Data[0] & 0xF0);
                if ((midiCommand == 0x90) || (midiCommand == 0x80))
                {
                    byte triggerNoteNum = midiInputEvent.Data[1];

                    if (_plugin.NoteMap.Contains(triggerNoteNum))
                    {
                        _plugin.hitCount++;

                        byte channel  = (byte)(midiInputEvent.Data[0] & 0x0F);
                        byte velocity = midiInputEvent.Data[2];

                        MapNoteItem item = _plugin.NoteMap[triggerNoteNum];

                        byte[] midiData = null;
                        if (midiCommand == 0x90)
                        {
                            midiData = MapNoteItem.StringToBytes(item.OutputBytesStringOn, channel, velocity);
                        }
                        else if (midiCommand == 0x80)
                        {
                            midiData = MapNoteItem.StringToBytes(item.OutputBytesStringOff, channel, velocity);
                        }
                        // else midiData remains null, which should never happen

                        // If OutputBytes was empty, ignore this event.   Could try sending the event with an empty array (not null) - not sure what would happen.
                        if (midiData == null)
                        {
                            continue;
                        }

                        // Trick: Use VstMidiSysExEvent in place of VstMidiEvent, since this seems to allow arbitary bytes.
                        VstMidiSysExEvent mappedEvent = new VstMidiSysExEvent(midiInputEvent.DeltaFrames, midiData);

                        Events.Add(mappedEvent);
                    }
                    else if (_plugin.midiThru)
                    {
                        // add original event
                        Events.Add(evnt);
                    }
                    // Otherwise ignore silently
                }
            }
        }