/****************
        * Constructors *
        ****************/

        #region Public Constructors

        /// <summary>Initializes a new instance of the MidiSysExEventDialog class.</summary>
        /// <param name="sysExEvent">
        /// MidiSysExEvent object representing the MIDI system exclusive
        /// (SysEx) message/event to edit, or null to create a new one.
        /// </param>
        public MidiSysExEventDialog(MidiSysExEvent sysExEvent)
            : base(sysExEvent)
        {
            int i = this.ControlCount;

            /* Initialize the "Escape" check box. */
            this.EscapeCheckBox = UI.CreateCheckBox(++i, MarginType.Standard, Properties.Resources.Escape, null);

            /* Initialize the "Data" controls. */
            this.DataLabel = UI.CreateLabel(MarginType.Standard, Properties.Resources.Data, true);
            DockPanel panel = MidiEventDialog.CreateDataPanel(ref this.DataHexTextBox, ref this.DataCommentTextBox, ++i);

            this.DataHexTextBox.TextChanged   += this.DataHexTextBox_TextChanged;
            this.DataCommentTextBox.IsReadOnly = true;
            this.DataLabel.Target = this.DataHexTextBox;

            /* Build out the window and its content. */
            this.AddUIElement(this.EscapeCheckBox);
            this.AddUIElement(this.DataLabel);
            this.AddUIElement(panel);
            this.BuildOut(UI.ClientWidth, MidiSysExEventDialog.TitleString);

            /* The OK button should start out disabled and stay that way until all required input is entered. */
            this.OkButton.IsEnabled = false;

            /* If a MidiSysExEvent object was supplied, use it to set initial values. */
            if (this.ForNewItem)
            {
                return;
            }
            this.DeltaTime = sysExEvent.DeltaTime;
            this.EscapeCheckBox.IsChecked = sysExEvent.Escape;
            this.DataHexTextBox.Text      = this.Hex = Midi.FormatHex(sysExEvent.Data, 0, sysExEvent.Data.Length);
        }
示例#2
0
        private MidiSysExEvent CreateSysExEvent(int offset, int deltaTime, bool escape, byte[] bytes)
        {
            MidiSysExEvent sysExEvent = new MidiSysExEvent(this, offset);

            sysExEvent.DeltaTime = deltaTime;
            sysExEvent.Escape    = escape;
            sysExEvent.Data      = bytes;
            return(sysExEvent);
        }
示例#3
0
        /// <summary>Inserts a new system exclusive (SysEx) message/event into this file at the specified index.</summary>
        /// <param name="index">The index in this file's list at which the event should be inserted.</param>
        /// <param name="deltaTime">The amount of time (in ticks) between the previous event in the track and this one.</param>
        /// <param name="escape">
        /// False indicates a regular SysEx message, which could be the first in a series of timed packets.
        /// True indicates a SysEx "escape," or the next in a series of timed packets.
        /// </param>
        /// <param name="bytes">Array of bytes containing the event data (not including the delta-time or status byte).</param>
        /// <returns>The new MidiSysExEvent object that is inserted.</returns>
        public MidiSysExEvent InsertSysExEvent(int index, int deltaTime, bool escape, byte[] bytes)
        {
            int n = MidiSysExEvent.SizeItem(0, 0), offset = this.Items[index].Offset;

            this.Resize(n, offset, index);
            MidiSysExEvent sysExEvent = this.CreateSysExEvent(offset, deltaTime, escape, bytes);

            this.Items.Insert(index, sysExEvent);
            this.SetTotalTime(index);
            return(sysExEvent);
        }
示例#4
0
        /// <summary>Adds a new system exclusive (SysEx) message/event to the end of this file.</summary>
        /// <param name="deltaTime">The amount of time (in ticks) between the previous event in the track and this one.</param>
        /// <param name="escape">
        /// False indicates a regular SysEx message, which could be the first in a series of timed packets.
        /// True indicates a SysEx "escape," or the next in a series of timed packets.
        /// </param>
        /// <param name="bytes">Array of bytes containing the event data (not including the delta-time or status byte).</param>
        /// <returns>The new MidiSysExEvent object that is added.</returns>
        public MidiSysExEvent AddSysExEvent(int deltaTime, bool escape, byte[] bytes)
        {
            int n = MidiSysExEvent.SizeItem(0, 0), offset = this.Bytes.Length;

            this.Resize(n, offset, this.ItemCount);
            MidiSysExEvent sysExEvent = this.CreateSysExEvent(offset, deltaTime, escape, bytes);

            this.Items.Add(sysExEvent);
            this.SetTotalTime(this.ItemCount - 1);
            return(sysExEvent);
        }
示例#5
0
        private void ParseEvents(int offset, int length, int trackNumber)
        {
            string        s;
            int           n = offset + length, i, j = 0;
            MidiEvent     mtrkEvent = null;
            MidiMetaEvent metaEvent;

            /* A track chunk is a stream of MIDI (MTrk) events.  Process each such
             * event in this part of the byte array comprising the track chunk.
             */
            for (i = offset; i < n; i += mtrkEvent.Size)
            {
                /* In order to know what kind of event to instantiate, we must read the event's status
                 * byte, which requires skipping past the delta-time (stored as a variable-length quantity).
                 */
                for (j = i; j < this.Bytes.Length && (this.Bytes[j] & 0x80) > 0; ++j)
                {
                    if (j - i > 3)
                    {
                        s = string.Format("{0} (@ {1} {2})", Properties.Resources.InvalidVLQ, Properties.Resources.Byte, i);
                        this.AddErrorText(s, trackNumber);
                        return;
                    }
                }
                if (++j >= this.Bytes.Length)
                {
                    break;
                }

                /* Instantiate an event object of the appropriate type (based on the status byte). */
                switch (this.Bytes[j])
                {
                case 0xFF: mtrkEvent = new MidiMetaEvent(this, i); break;

                case 0xF7: mtrkEvent = new MidiSysExEvent(this, i); break;

                case 0xF0: mtrkEvent = new MidiSysExEvent(this, i); break;

                default: mtrkEvent = new MidiChannelEvent(this, i); break;
                }
                this.Items.Add(mtrkEvent);
                this.SetTotalTime(this.ItemCount - 1);

                /* If the event is a MIDI channel message/event that does not use
                 * running status, use it to set the running status at this byte offset.
                 */
                if (++j >= this.Bytes.Length)
                {
                    break;
                }
                MidiChannelEvent channelEvent = mtrkEvent as MidiChannelEvent;
                if (channelEvent != null && !channelEvent.RunningStatus)
                {
                    this.SetRunningStatus(i, channelEvent.Status);
                }

                /* If the event is a meta-event representing a key signature,
                 * use it to set the key signature at the appropriate time.
                 */
                if (++j >= this.Bytes.Length)
                {
                    break;
                }
                metaEvent = MidiFile.ItemToKeySignatureEvent(mtrkEvent);
                if (metaEvent != null)
                {
                    this.SetKeySignature(metaEvent);
                }
            }

            /* If we ran out of data, add an error message. */
            if (j >= this.Bytes.Length)
            {
                s = string.Format(Properties.Resources.MismatchFormat, Properties.Resources.Byte, length, i - offset);
                this.AddErrorText(s, trackNumber);
            }

            /* The last event in a track chunk should be an End of Track meta-event. */
            metaEvent = mtrkEvent as MidiMetaEvent;
            if (metaEvent == null || (metaEvent != null && metaEvent.Type != MidiMetaEvent.EndOfTrackType))
            {
                this.AddErrorText(Properties.Resources.NoEndOfTrack, trackNumber);
            }
        }