コード例 #1
0
ファイル: SMF.cs プロジェクト: peterempson/musicinator
        SmfMessage ReadMessage(int deltaTime)
        {
            byte b = PeekByte();

            running_status = b < 0x80 ? running_status : ReadByte();
            int len;

            switch (running_status)
            {
            case SmfEvent.SysEx1:
            case SmfEvent.SysEx2:
            case SmfEvent.Meta:
                byte metaType = running_status == SmfEvent.Meta ? ReadByte() : (byte)0;
                len = ReadVariableLength();
                byte [] args = new byte [len];
                if (len > 0)
                {
                    ReadBytes(args);
                }
                return(new SmfMessage(deltaTime, new SmfEvent(running_status, metaType, 0, args)));

            default:
                int value = running_status;
                value += ReadByte() << 8;
                if (SmfEvent.FixedDataSize(running_status) == 2)
                {
                    value += ReadByte() << 16;
                }
                return(new SmfMessage(deltaTime, new SmfEvent(value)));
            }
        }
コード例 #2
0
ファイル: MidiPlayer.cs プロジェクト: peterempson/musicinator
        public MidiPlayer(SmfMusic music, IMidiOutput output, IMidiTimeManager timeManager)
        {
            if (music == null)
            {
                throw new ArgumentNullException("music");
            }
            if (output == null)
            {
                throw new ArgumentNullException("output");
            }
            if (timeManager == null)
            {
                throw new ArgumentNullException("timeManager");
            }

            this.output = output;

            player         = new MidiSyncPlayer(music, timeManager);
            EventReceived += (m) => {
                switch (m.EventType)
                {
                case SmfEvent.SysEx1:
                case SmfEvent.SysEx2:
                    if (buffer.Length <= m.Data.Length)
                    {
                        buffer = new byte [buffer.Length * 2];
                    }
                    buffer [0] = m.StatusByte;
                    Array.Copy(m.Data, 0, buffer, 1, m.Data.Length);
                    output.SendAsync(buffer, 0, m.Data.Length + 1, 0);
                    break;

                case SmfEvent.Meta:
                    // do nothing.
                    break;

                default:
                    var size = SmfEvent.FixedDataSize(m.StatusByte);
                    buffer [0] = m.StatusByte;
                    buffer [1] = m.Msb;
                    buffer [2] = m.Lsb;
                    output.SendAsync(buffer, 0, size + 1, 0);
                    break;
                }
            };
        }
コード例 #3
0
ファイル: SMF.cs プロジェクト: peterempson/musicinator
        public void WriteTrack(SmfTrack track)
        {
            stream.Write(Encoding.UTF8.GetBytes("MTrk"), 0, 4);
            WriteInt(GetTrackDataSize(track));

            byte running_status = 0;

            foreach (SmfMessage e in track.Messages)
            {
                Write7BitVariableInteger(e.DeltaTime);
                switch (e.Event.EventType)
                {
                case SmfEvent.Meta:
                    meta_event_writer(false, e, stream);
                    break;

                case SmfEvent.SysEx1:
                case SmfEvent.SysEx2:
                    stream.WriteByte(e.Event.EventType);
                    Write7BitVariableInteger(e.Event.Data.Length);
                    stream.Write(e.Event.Data, 0, e.Event.Data.Length);
                    break;

                default:
                    if (DisableRunningStatus || e.Event.StatusByte != running_status)
                    {
                        stream.WriteByte(e.Event.StatusByte);
                    }
                    int len = SmfEvent.FixedDataSize(e.Event.EventType);
                    stream.WriteByte(e.Event.Msb);
                    if (len > 1)
                    {
                        stream.WriteByte(e.Event.Lsb);
                    }
                    if (len > 2)
                    {
                        throw new Exception("Unexpected data size: " + len);
                    }
                    break;
                }
                running_status = e.Event.StatusByte;
            }
        }
コード例 #4
0
ファイル: SMF.cs プロジェクト: peterempson/musicinator
        int GetTrackDataSize(SmfTrack track)
        {
            int  size           = 0;
            byte running_status = 0;

            foreach (SmfMessage e in track.Messages)
            {
                // delta time
                size += GetVariantLength(e.DeltaTime);

                // arguments
                switch (e.Event.EventType)
                {
                case SmfEvent.Meta:
                    size += meta_event_writer(true, e, null);
                    break;

                case SmfEvent.SysEx1:
                case SmfEvent.SysEx2:
                    size++;
                    size += GetVariantLength(e.Event.Data.Length);
                    size += e.Event.Data.Length;
                    break;

                default:
                    // message type & channel
                    if (DisableRunningStatus || running_status != e.Event.StatusByte)
                    {
                        size++;
                    }
                    size += SmfEvent.FixedDataSize(e.Event.EventType);
                    break;
                }

                running_status = e.Event.StatusByte;
            }
            return(size);
        }