2 Epichord - a midi sequencer
3 Copyright (C) 2008 Evan Rinehart
5 This program is free software; you can redistribute it and/or
6 modify it under the terms of the GNU General Public License
7 as published by the Free Software Foundation; either version 2
8 of the License, or (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to
18 The Free Software Foundation, Inc.
19 51 Franklin Street, Fifth Floor
20 Boston, MA 02110-1301, USA
26 #define MIDI_NOTE_OFF 0x80
27 #define MIDI_NOTE_ON 0x90
28 #define MIDI_AFTERTOUCH 0xA0
29 #define MIDI_CONTROLLER_CHANGE 0xB0
30 #define MIDI_PROGRAM_CHANGE 0xC0
31 #define MIDI_CHANNEL_PRESSURE 0xD0
32 #define MIDI_PITCH_WHEEL 0xE0
34 #define MAX_TRACK_NAME 256
45 int dur
; //for note on events
47 //struct mevent* off; //for note on events
48 //int off_index; //used when reloading
66 mevent(int ztype
, int ztick
, int zv1
){
88 selected
= e
->selected
;
89 modified
= e
->modified
;
96 struct mevent
* events
;
100 unsigned char r1
,g1
,b1
;//main color
101 unsigned char r2
,g2
,b2
;//bottom color
102 unsigned char r3
,g3
,b3
;//top color
103 unsigned char rx
,gx
,bx
;//xray color
105 float h
, s
, v
; //color
127 void push_new(pattern
* p
);
133 layerstack(pattern
* p
);
149 // unsigned char color[3][3];
152 int record_flag
;//0=on record, erase/save. 1=dont
156 int scrollx
, scrolly
;
165 void record_check(int mode
);
182 seqpat(int ztrack
, int ztick
, int zdur
, pattern
* zp
){
211 scrollx
= zs
->scrollx
;
212 scrolly
= zs
->scrolly
;
214 selected
= zs
->selected
;
215 modified
= zs
->modified
;
223 seqpat(seqpat
* zs
, pattern
* zp
){
235 scrollx
= zs
->scrollx
;
236 scrolly
= zs
->scrolly
;
238 selected
= zs
->selected
;
239 modified
= zs
->modified
;
256 if(layers
->ref_c
== 0){
278 char name
[MAX_TRACK_NAME
];
298 head
= new seqpat(0,0,0,new pattern());
320 void tswap(T
* old
, T
* nu
){
321 nu
->next
= old
->next
;
322 nu
->prev
= old
->prev
;
325 old
->prev
->next
= nu
; //'atomic'
328 old
->next
->prev
= nu
; //prev ptrs are only read by gui thread
333 void tremove(T
* old
){
335 old
->prev
->next
= old
->next
; //'atomic'
338 old
->next
->prev
= old
->prev
; //prev ptrs are only read by gui thread
343 void tinsert(T
* targ
, T
* nu
){
345 nu
->next
= targ
->next
;
347 targ
->next
= nu
; //'atomic'
349 nu
->next
->prev
= nu
; //prev ptrs are only read by gui thread
354 T
* tfind(T
* begin
, int tick
){
357 if(ptr
->next
->tick
> tick
){
365 mevent
* find_off(mevent
* e
);
372 virtual void undo() {}
373 virtual void redo() {}
377 void set_undo(Command
* c
);
378 void push_undo(int n
);
382 int clear_undos(int number
);
386 class CreateSeqpat
: public Command
{
393 CreateSeqpat(int track
, int tick
, seqpat
* zs
, int copy
);
396 if(s
->p
->ref_c
-- == 0){
406 class CreateSeqpatBlank
: public CreateSeqpat
{
410 CreateSeqpatBlank(int track
, int tick
, int len
);
415 class DeleteSeqpat
: public Command
{
420 DeleteSeqpat(seqpat
* zs
){
428 class ResizeSeqpat
: public Command
{
434 ResizeSeqpat(seqpat
* zs
, int dur
){
447 class MoveSeqpat
: public Command
{
449 seqpat
*targ1
, *targ2
;
455 MoveSeqpat(seqpat
* zs
, int track
, int tick
);
461 class SplitSeqpat
: public Command
{
468 SplitSeqpat(seqpat
* zs
){
476 if(--(p2
->ref_c
) == 0){
488 class CreateNote
: public Command
{
495 CreateNote(pattern
* zp
, int note
, int vel
, int tick
, int dur
){
497 e1
= new mevent(MIDI_NOTE_ON
, tick
, note
);
500 e2
= new mevent(MIDI_NOTE_OFF
, tick
+dur
, note
);
502 //e->off = new mevent(MIDI_NOTE_OFF, tick+dur, note);
514 class CreateNoteOn
: public Command
{
520 CreateNoteOn(pattern
* zp
, int note
, int vel
, int tick
, int dur
){
522 e1
= new mevent(MIDI_NOTE_ON
, tick
, note
);
534 class CreateNoteOff
: public Command
{
544 CreateNoteOff(pattern
* zp
, int note
, int vel
, int tick
);
553 class DeleteNote
: public Command
{
560 DeleteNote(pattern
* zp
, mevent
* ze
){
570 class MoveNote
: public Command
{
583 MoveNote(pattern
* zp
, mevent
* ze
, int zt
, int znote
){
598 class ResizeNote
: public Command
{
607 ResizeNote(pattern
* zp
, mevent
* ze
, int dur
);
620 class CreateEvent
: public Command
{
626 CreateEvent(pattern
* zp
, int type
, int tick
, int value1
, int value2
){
628 e
= new mevent(type
,tick
,value1
);
630 e
->prev
= tfind
<mevent
>(zp
->events
,tick
);
631 e
->next
= e
->prev
->next
;
641 class DeleteEvent
: public Command
{
646 DeleteEvent(mevent
* ze
){
654 class ChangeEvent
: public Command
{
660 ChangeEvent(mevent
* ze
, int zv1
, int zv2
){
675 int play_seq(int cur_tick
, void (*dispatch_event
)(mevent
*, int port
, int tick
));
676 int set_seq_pos(int new_tick
);
678 void set_rec_track(int t
);
681 int set_default_hsv_value(float v
);
683 void set_undo(Command
* c
);
684 void undo_push(int n
);
688 void pattern_clear();
689 void reset_record_flags();
692 //encodes data in e as a midi event placed in buf
693 int midi_encode(mevent
* e
, int chan
, unsigned char* buf
, size_t* n
);
695 //decodes midi data and creates a new mevent
696 int midi_decode(char* buf
, mevent
* e
);