Cross Platform Application to allow control with a MIDI controller
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

84 lines
3.0 KiB

// Author: Gockner, Simon
// Created: 2021-04-09
// Copyright(c) 2021 SimonG. All Rights Reserved.
using System;
using System.Collections.Generic;
using System.Linq;
using Lib.Driver.Interfaces;
using Lib.Midi.Interfaces;
using Lib.Midi.Messages.Factories;
using Lib.Midi.Messages.Interfaces;
using NAudio.Midi;
namespace Lib.Midi
{
public class MidiCommunication : IMidiCommunication
{
private readonly IDriver _driver;
private readonly IMidiMessageFactory _midiMessageFactory;
private MidiIn? _midiIn;
private MidiOut? _midiOut;
public MidiCommunication(IDriver driver, IMidiMessageFactory midiMessageFactory)
{
_driver = driver;
_midiMessageFactory = midiMessageFactory;
}
private IEnumerable<(MidiInCapabilities midiInCapabilities, int index)> MidiInputs
{
get
{
for (int i = 0; i < MidiIn.NumberOfDevices; i++)
yield return (MidiIn.DeviceInfo(i), i);
}
}
private IEnumerable<(MidiOutCapabilities midiOutCapabilities, int index)> MidiOutputs
{
get
{
for (int i = 0; i < MidiOut.NumberOfDevices; i++)
yield return (MidiOut.DeviceInfo(i), i);
}
}
public void Open(bool useMidiView)
{
int inputProductId = useMidiView ? MidiView.INPUT_PRODUCT_ID : _driver.InputProductId;
int outputProductId = useMidiView ? MidiView.OUTPUT_PRODUCT_ID : _driver.OutputProductId;
var midiInput = MidiInputs.FirstOrDefault(i => i.midiInCapabilities.ProductId == inputProductId);
var midiOutput = MidiOutputs.FirstOrDefault(o => o.midiOutCapabilities.ProductId == outputProductId);
_midiIn = new MidiIn(midiInput.index);
_midiOut = new MidiOut(midiOutput.index);
_midiIn.MessageReceived += OnMidiInMessageReceived;
_midiIn.ErrorReceived += OnMidiInErrorReceived;
_midiIn.Start();
}
public void Close()
{
if (_midiIn != null)
{
_midiIn.Stop();
_midiIn.MessageReceived -= OnMidiInMessageReceived;
_midiIn.ErrorReceived -= OnMidiInErrorReceived;
_midiIn.Close();
}
_midiOut?.Close();
}
public void Send(IMidiMessage message) => _midiOut?.Send(message.RawMessage);
private void OnMidiInMessageReceived(object? sender, MidiInMessageEventArgs args) => MessageReceived?.Invoke(this, _midiMessageFactory.Create(args.MidiEvent));
private void OnMidiInErrorReceived(object? sender, MidiInMessageEventArgs args) => ErrorReceived?.Invoke(this, _midiMessageFactory.Create(args.MidiEvent));
public event EventHandler<IMidiMessage>? MessageReceived;
public event EventHandler<IMidiMessage>? ErrorReceived;
}
}