/*
 * Copyright 1998-2002 Sun Microsystems, Inc.  All Rights Reserved.
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 *
 * This code is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License version 2 only, as
 * published by the Free Software Foundation.  Sun designates this
 * particular file as subject to the "Classpath" exception as provided
 * by Sun in the LICENSE file that accompanied this code.
 *
 * This code is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 * version 2 for more details (a copy is included in the LICENSE file that
 * accompanied this code).
 *
 * You should have received a copy of the GNU General Public License version
 * 2 along with this work; if not, write to the Free Software Foundation,
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 *
 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
 * CA 95054 USA or visit www.sun.com if you need additional information or
 * have any questions.
 */

package javax.sound.midi;

/**
 * <code>MidiMessage</code> is the base class for MIDI messages.  They include
 * not only the standard MIDI messages that a synthesizer can respond to, but also
 * "meta-events" that can be used by sequencer programs.  There are meta-events
 * for such information as lyrics, copyrights, tempo indications, time and key
 * signatures, markers, etc.  For more information, see the Standard MIDI Files 1.0
 * specification, which is part of the Complete MIDI 1.0 Detailed Specification
 * published by the MIDI Manufacturer's Association
 * (<a href = http://www.midi.org>http://www.midi.org</a>).
 * <p>
 * The base <code>MidiMessage</code> class provides access to three types of
 * information about a MIDI message:
 * <ul>
 * <li>The messages's status byte</li>
 * <li>The total length of the message in bytes (the status byte plus any data bytes)</li>
 * <li>A byte array containing the complete message</li>
 * </ul>
 *
 * <code>MidiMessage</code> includes methods to get, but not set, these values.
 * Setting them is a subclass responsibility.
 * <p>
 * <a name="integersVsBytes"></a>
 * The MIDI standard expresses MIDI data in bytes.  However, because
 * Java<sup>TM</sup> uses signed bytes, the Java Sound API uses integers
 * instead of bytes when expressing MIDI data.  For example, the
 * {@link #getStatus()} method of
 * <code>MidiMessage</code> returns MIDI status bytes as integers.  If you are
 * processing MIDI data that originated outside Java Sound and now
 * is encoded as signed bytes, the bytes can
 * can be converted to integers using this conversion:
 * <center><code>int i = (int)(byte & 0xFF)</code></center>
 * <p>
 * If you simply need to pass a known MIDI byte value as a method parameter,
 * it can be expressed directly as an integer, using (for example) decimal or
 * hexidecimal notation.  For instance, to pass the "active sensing" status byte
 * as the first argument to ShortMessage's
 * {@link ShortMessage#setMessage(int) setMessage(int)}
 * method, you can express it as 254 or 0xFE.
 *
 * @see Track
 * @see Sequence
 * @see Receiver
 *
 * @author David Rivas
 * @author Kara Kytle
 */

public abstract class MidiMessage implements Cloneable {

    // Instance variables

    /**
     * The MIDI message data.  The first byte is the status
     * byte for the message; subsequent bytes up to the length
     * of the message are data bytes for this message.
     * @see #getLength
     */
    protected byte[] data;


    /**
     * The number of bytes in the MIDI message, including the
     * status byte and any data bytes.
     * @see #getLength
     */
    protected int length = 0;


    /**
     * Constructs a new <code>MidiMessage</code>.  This protected
     * constructor is called by concrete subclasses, which should
     * ensure that the data array specifies a complete, valid MIDI
     * message.
     *
     * @param data an array of bytes containing the complete message.
     * The message data may be changed using the <code>setMessage</code>
     * method.
     *
     * @see #setMessage
     */
    protected MidiMessage(byte[] data) {
        this.data = data;
        if (data != null) {
            this.length = data.length;
        }
    }


    /**
     * Sets the data for the MIDI message.   This protected
     * method is called by concrete subclasses, which should
     * ensure that the data array specifies a complete, valid MIDI
     * message.
     */
    protected void setMessage(byte[] data, int length) throws InvalidMidiDataException {
        if (length < 0 || (length > 0 && length > data.length)) {
            throw new IndexOutOfBoundsException("length out of bounds: "+length);
        }
        this.length = length;

        if (this.data == null || this.data.length < this.length) {
            this.data = new byte[this.length];
        }
        System.arraycopy(data, 0, this.data, 0, length);
    }


    /**
     * Obtains the MIDI message data.  The first byte of the returned byte
     * array is the status byte of the message.  Any subsequent bytes up to
     * the length of the message are data bytes.  The byte array may have a
     * length which is greater than that of the actual message; the total
     * length of the message in bytes is reported by the <code>{@link #getLength}</code>
     * method.
     *
     * @return the byte array containing the complete <code>MidiMessage</code> data
     */
    public byte[] getMessage() {
        byte[] returnedArray = new byte[length];
        System.arraycopy(data, 0, returnedArray, 0, length);
        return returnedArray;
    }


    /**
     * Obtains the status byte for the MIDI message.  The status "byte" is
     * represented as an integer; see the
     * <a href="#integersVsBytes">discussion</a> in the
     * <code>MidiMessage</code> class description.
     *
     * @return the integer representation of this event's status byte
     */
    public int getStatus() {
        if (length > 0) {
            return (data[0] & 0xFF);
        }
        return 0;
    }


    /**
     * Obtains the total length of the MIDI message in bytes.  A
     * MIDI message consists of one status byte and zero or more
     * data bytes.  The return value ranges from 1 for system real-time messages,
     * to 2 or 3 for channel messages, to any value for meta and system
     * exclusive messages.
     *
     * @return the length of the message in bytes
     */
    public int getLength() {
        return length;
    }


    /**
     * Creates a new object of the same class and with the same contents
     * as this object.
     * @return a clone of this instance.
     */
    public abstract Object clone();
}
