在c#中停止midi音符缓冲

时间:2016-10-28 09:25:40

标签: c# midi

我已经在C#中创建了一个程序,让我的孩子们在阅读音乐时测试它们。它以设定的间隔显示随机音符(由计时器确定),然后根据键盘的输入检查当前显示的音符,看它们是否正确。它工作得很好,除了一次意外按下两个音符的事实,其中第二个音符被认为是后续音符的预期答案,它甚至还没有被显示出来!我假设在音乐键盘上弹奏的音符存储在缓冲区中,然后在下次需要时使用。我希望能够清理干净的石板"当屏幕上显示新笔记时,将忽略任何先前的输入。我很高兴有任何关于如何做到这一点的想法。

部分代码如下:

using System;
using Midi;
using System.Media;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Threading;

namespace WindowsFormsApplication6
{
    public partial class Form1 : Form
    {

        private void Form1_Load(object sender, EventArgs e)
        {
            // Create persistent delegates which we can add and remove to events.
            noteOnHandler = new InputDevice.NoteOnHandler(this.NoteOn);
            noteOffHandler = new InputDevice.NoteOffHandler(this.NoteOff);
            InputDevice preferredInputDevice = InputDevice.InstalledDevices[0];
            UseInputDevice(InputDevice.InstalledDevices[0]);
        }

        private void UseInputDevice(InputDevice newInputDevice)
        {
            if (newInputDevice == inputDevice)
            {
                return;
            }
            if (inputDevice != null)
            {
                if (inputDevice.IsOpen)
                {
                    if (inputDevice.IsReceiving)
                    {
                        inputDevice.StopReceiving();
                    }
                    inputDevice.Close();
                }
                inputDevice.NoteOn -= noteOnHandler;
                inputDevice.NoteOff -= noteOffHandler;
            }
            inputDevice = newInputDevice;
            inputDevice.NoteOn += noteOnHandler;
            inputDevice.NoteOff += noteOffHandler;
            inputDevice.Open();
            inputDevice.StartReceiving(null);
        }

        // Method called when the input device receives a NoteOn message.  Updates
        // the input status label.  Respects GUI thread affinity by invoking to the
        // GUI thread if necessary.
        public void NoteOn(NoteOnMessage msg)
        {
            if (button1.Text == "STOP")
            {
                if (InvokeRequired)
                {
                    BeginInvoke(noteOnHandler, msg);
                    return;
                }
                if (string.Equals(String.Format("{0}", msg.Pitch), notename)) { currentscore++; correct[numberofnotes] = true; using (SoundPlayer player = new SoundPlayer("chime_up.wav")) { player.PlaySync(); } }
                else { using (SoundPlayer player = new SoundPlayer("klaxon_ahooga.wav")) { player.PlaySync(); } correct[numberofnotes] = false; }
                outof++;
                score.Text = String.Format("{0}", currentscore);
                notesshown.Text = String.Format("{0}", outof);
                numberofticks = 0;
                if (outof < 20) { generate_note(); }
                Redrawit();
                Invalidate();
                if (outof == 20) { reset_screen(); }
            }
        }

        // Method called when the input device receives a NoteOff message.  Updates
        // the input status label.  Respects GUI thread affinity by invoking to the
        // GUI thread if necessary.
        public void NoteOff(NoteOffMessage msg)
        {
            if (InvokeRequired)
            {
                BeginInvoke(noteOffHandler, msg);
                return;
            }
        }

        // Persistent delegate objects for the note handlers.
        private InputDevice.NoteOnHandler noteOnHandler;
        private InputDevice.NoteOffHandler noteOffHandler;
    }
}

0 个答案:

没有答案