]> ruin.nu Git - moosique.git/blob - MooNote.java
hmm.. this doesn't want to work..
[moosique.git] / MooNote.java
1 import javax.sound.midi.*;
2
3 /**
4  * Functional representation of a MIDI note, which adds functionality to the existent MidiEvent class.
5  * Also provides a reference to the corresponding NoteOff event.
6  * 
7  * @author  Einar Pehrson
8  */
9  
10 public class MooNote extends MidiEvent {
11
12         protected MidiEvent noteOffEvent;
13         protected ShortMessage noteOnMsg, noteOffMsg;
14
15         /** 
16          * Creates a MooNote from the given NoteOn event in the current track.
17          * @param noteOnEvent   the NoteOn event of the note
18          */
19         public MooNote (MidiEvent noteOnEvent) {
20                 super(noteOnEvent.getMessage(), noteOnEvent.getTick());
21                 noteOnMsg = (ShortMessage)getMessage();
22         }
23
24         /** 
25          * Creates a MooNote from the given NoteOn event in the current track and creates a reference to
26          * the corresponding NoteOff event.
27          * @param noteOnEvent   the NoteOn event of the note
28          * @param noteOffEvent  the NoteOff event of the note
29          */
30         public MooNote (MidiEvent noteOnEvent, MidiEvent noteOffEvent) {
31                 super(noteOnEvent.getMessage(), noteOnEvent.getTick());
32                 this.noteOffEvent = noteOffEvent;
33                 noteOnMsg = (ShortMessage)getMessage();
34                 noteOffMsg = (ShortMessage)noteOffEvent.getMessage();
35         }
36
37         /** 
38          * Creates a MooNote of the given pitch, velocity and duration in the current track.
39          * @param channel       the channel of the note (1-16)
40          * @param pitch         the pitch of the note (0-127)
41          * @param velocity      the velocity of the note (0-127)
42          * @param timestamp     the timestamp of the note in ticks (96 per beat)
43          * @param duration      the duration of the note in ticks (96 per beat)
44          */
45         public MooNote (int channel, int pitch, int velocity, long timestamp, int duration) {
46                 super(new ShortMessage(), timestamp);
47                 noteOffEvent = new MidiEvent(new ShortMessage(), timestamp + duration);
48                 noteOnMsg = (ShortMessage)getMessage();
49                 noteOffMsg = (ShortMessage)noteOffEvent.getMessage();
50                 try {
51                         noteOnMsg.setMessage(ShortMessage.NOTE_ON, channel, pitch, velocity);
52                         noteOffMsg.setMessage(ShortMessage.NOTE_OFF, channel, pitch, 0);
53                 } catch (InvalidMidiDataException e) {System.out.println("Invalid data!");}
54         }
55
56         /** 
57          * Sets the channel of the current note.
58          * @param channel       the channel of the note (1-16)
59          */
60         public void setChannel(int channel) {
61                 try {
62                         noteOnMsg.setMessage(noteOnMsg.getCommand(), (byte)channel, noteOnMsg.getData1(), noteOnMsg.getData2());
63                         if(hasNoteOffEvent()) noteOffMsg.setMessage(noteOffMsg.getCommand(), (byte)channel, noteOffMsg.getData1(), noteOffMsg.getData2());
64                 } catch (InvalidMidiDataException e) {}
65         }
66
67         /** 
68          * Sets the pitch of the current note.
69          * @param pitch         the pitch of the note (0-127)
70          */
71         public void setPitch(int pitch) {
72                 try {
73                         noteOnMsg.setMessage(noteOnMsg.getCommand(), noteOnMsg.getChannel(), (byte)pitch, noteOnMsg.getData2());
74                         if(hasNoteOffEvent()) noteOffMsg.setMessage(noteOffMsg.getCommand(), noteOffMsg.getChannel(), (byte)pitch, noteOffMsg.getData2());
75                 } catch (InvalidMidiDataException e) {}
76         }
77
78         /** 
79          * Sets the velocity of the current note.
80          * @param vel   the velocity of the note (0-127)
81          */
82         public void setVelocity(int vel) {
83                 try {
84                         noteOnMsg.setMessage(noteOnMsg.getCommand(), noteOnMsg.getChannel(), noteOnMsg.getData1(), (byte)vel);
85                         if(hasNoteOffEvent()) noteOffMsg.setMessage(noteOffMsg.getCommand(), noteOffMsg.getChannel(), noteOffMsg.getData1(), noteOffMsg.getData2());
86                 } catch (InvalidMidiDataException e) {}
87         }
88
89         /** 
90          * Sets the duration of the current note (or rather moves the note off event).
91          * @param n     the duration of the note in ticks (96 per beat)
92          */
93         public void setDuration(int ticks) {
94                 if (hasNoteOffEvent()) noteOffEvent.setTick(getTick() + ticks);
95         }
96
97         /** 
98          * Sets the timestamp of the current note.
99          * @param tick  the timestamp of the note in ticks (96 per beat)
100          */
101         public void setTick(long tick) {
102                 if (hasNoteOffEvent()) noteOffEvent.setTick(tick +  getDuration());
103                 super.setTick(tick);
104         }
105
106         /** 
107          * Returns the channel of the current note.
108          * @return the channel of the note (1-16)
109          */
110         public int getChannel() {
111                 return noteOnMsg.getChannel();
112         }
113
114         /** 
115          * Returns the pitch of the current note.
116          * @return the pitch of the note (0-127)
117          */
118         public int getPitch() {
119                 return noteOnMsg.getData1();
120         }
121
122         /** 
123          * Returns the velocity of the current note.
124          * @return the velocity of the note (0-127)
125          */
126         public int getVelocity() {
127                 return noteOnMsg.getData2();
128         }
129
130         /** 
131          * Returns the duration of the current note.
132          * @return the duration of the note (in ticks)
133          */
134         public int getDuration() {
135                 if (!hasNoteOffEvent()) return 0;
136                 return (int)(noteOffEvent.getTick() - getTick());
137         }
138
139         /** 
140          * Returns whether the NoteOff event was found.
141          * @return      the note off MidiEvent
142          */
143         public boolean hasNoteOffEvent() {
144                 return noteOffEvent != null;
145         }
146
147         /**
148          * Adds this note (both noteOn and noteOffEvents) to a track.
149          * @param track the track it'll be added to.
150          */
151         public void addTo(Track track){
152                 track.add(this);
153                 if (hasNoteOffEvent()) track.add(noteOffEvent);
154         }
155         
156         /**
157          * Removes this note (both noteOn and noteOffEvents) from a track.
158          * @param track the track it'll be removed from.
159          */
160         public void removeFrom(Track track){
161                 track.remove(this);
162                 if (hasNoteOffEvent()) track.remove(noteOffEvent);
163         }
164 }