Subversion Repositories svn.mios32

Rev

Rev 137 | Rev 166 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
134 tk 1
// $Id: seq_ui.c 159 2008-12-06 01:33:47Z tk $
2
/*
3
 * User Interface Routines
4
 *
5
 * ==========================================================================
6
 *
7
 *  Copyright (C) 2008 Thorsten Klose (tk@midibox.org)
8
 *  Licensed for personal non-commercial use only.
9
 *  All other rights reserved.
10
 *
11
 * ==========================================================================
12
 */
13
 
14
/////////////////////////////////////////////////////////////////////////////
15
// Include files
16
/////////////////////////////////////////////////////////////////////////////
17
 
18
#include <mios32.h>
19
 
20
#if DEFAULT_SRM_ENABLED
21
#include <blm8x8.h>
22
#endif
23
 
24
#include "seq_ui.h"
25
#include "seq_lcd.h"
26
#include "seq_led.h"
27
#include "seq_midi.h"
159 tk 28
#include "seq_bpm.h"
134 tk 29
#include "seq_core.h"
30
#include "seq_par.h"
31
#include "seq_trg.h"
32
 
33
 
34
/////////////////////////////////////////////////////////////////////////////
35
// Local types
36
/////////////////////////////////////////////////////////////////////////////
37
 
38
 
39
/////////////////////////////////////////////////////////////////////////////
40
// Local prototypes
41
/////////////////////////////////////////////////////////////////////////////
42
 
43
 
44
/////////////////////////////////////////////////////////////////////////////
45
// Global variables
46
/////////////////////////////////////////////////////////////////////////////
47
 
159 tk 48
u8 seq_ui_display_update_req;
49
u8 seq_ui_display_init_req;
134 tk 50
 
51
u8 ui_selected_group;
52
u8 ui_selected_tracks;
53
u8 ui_selected_par_layer;
54
u8 ui_selected_trg_layer;
55
u8 ui_selected_step_view;
56
u8 ui_selected_step;
57
 
58
u16 ui_gp_leds;
59
 
60
 
61
/////////////////////////////////////////////////////////////////////////////
62
// Local variables
63
/////////////////////////////////////////////////////////////////////////////
64
 
65
 
66
/////////////////////////////////////////////////////////////////////////////
67
// Initialisation
68
/////////////////////////////////////////////////////////////////////////////
69
s32 SEQ_UI_Init(u32 mode)
70
{
71
  // init selection variables
72
  ui_selected_group = 0;
73
  ui_selected_tracks = (1 << 0);
74
  ui_selected_par_layer = 0;
75
  ui_selected_trg_layer = 0;
76
  ui_selected_step_view = 0;
77
  ui_selected_step = 0;
78
 
79
  // visible GP pattern
80
  ui_gp_leds = 0x0000;
81
 
82
  // request display initialisation
159 tk 83
  seq_ui_display_init_req = 1;
134 tk 84
 
85
  return 0; // no error
86
}
87
 
88
 
89
/////////////////////////////////////////////////////////////////////////////
90
// Dedicated button functions
91
// Mapped to physical buttons in SEQ_UI_Button_Handler()
92
// Will also be mapped to MIDI keys later (for MIDI remote function)
93
/////////////////////////////////////////////////////////////////////////////
94
static s32 SEQ_UI_Button_GP(s32 depressed, u32 gp)
95
{
96
  if( depressed ) return -1; // ignore when button depressed
97
 
98
  // toggle trigger layer
99
  u8 visible_track = SEQ_UI_VisibleTrackGet();
100
  u8 step = gp + ui_selected_step_view*16;
101
  trg_layer_value[visible_track][ui_selected_trg_layer][step>>3] ^= (1 << (step&7));
102
 
103
  return 0; // no error
104
}
105
 
106
static s32 SEQ_UI_Button_Left(s32 depressed)
107
{
108
  if( depressed ) return -1; // ignore when button depressed
109
 
110
  if( played_step ) // tmp.
111
    --played_step;
112
 
113
  return 0; // no error
114
}
115
 
116
static s32 SEQ_UI_Button_Right(s32 depressed)
117
{
118
  if( depressed ) return -1; // ignore when button depressed
119
 
120
  if( ++played_step >= SEQ_CORE_NUM_STEPS ) // tmp.
121
    played_step = 0;
122
 
123
  return 0; // no error
124
}
125
 
126
static s32 SEQ_UI_Button_Scrub(s32 depressed)
127
{
137 tk 128
#if 0
134 tk 129
  if( depressed ) return -1; // ignore when button depressed
137 tk 130
#else
131
  // Sending SysEx Stream test
132
  u8 buffer[7] = { 0xf0, 0x11, 0x22, 0x33, 0x44, depressed ? 0x00 : 0x55, 0xf7 };
134 tk 133
 
137 tk 134
  MIOS32_MIDI_SendSysEx(DEFAULT, buffer, 7);
135
#endif
136
 
134 tk 137
  return 0; // no error
138
}
139
 
140
static s32 SEQ_UI_Button_Metronome(s32 depressed)
141
{
137 tk 142
#if 0
134 tk 143
  if( depressed ) return -1; // ignore when button depressed
137 tk 144
#else
145
  // Sending MIDI Note test
146
  if( depressed )
147
    MIOS32_MIDI_SendNoteOff(DEFAULT, 0x90, 0x3c, 0x00);
148
  else
149
    MIOS32_MIDI_SendNoteOn(DEFAULT, 0x90, 0x3c, 0x7f);
150
#endif
134 tk 151
 
152
  return 0; // no error
153
}
154
 
155
static s32 SEQ_UI_Button_Stop(s32 depressed)
156
{
157
  if( depressed ) return -1; // ignore when button depressed
158
 
159 tk 159
  // if sequencer running: stop it
160
  // if sequencer already stopped: reset song position
161
  if( seq_core_state_run )
162
    SEQ_CORE_Stop(0);
163
  else
164
    SEQ_CORE_Reset();
165
 
134 tk 166
  return 0; // no error
167
}
168
 
169
static s32 SEQ_UI_Button_Pause(s32 depressed)
170
{
171
  if( depressed ) return -1; // ignore when button depressed
172
 
159 tk 173
  // pause sequencer
174
  SEQ_CORE_Pause(0);
175
 
134 tk 176
  return 0; // no error
177
}
178
 
179
static s32 SEQ_UI_Button_Play(s32 depressed)
180
{
181
  if( depressed ) return -1; // ignore when button depressed
182
 
159 tk 183
  // start sequencer
184
  SEQ_CORE_Start(0);
185
 
134 tk 186
  return 0; // no error
187
}
188
 
189
static s32 SEQ_UI_Button_Rew(s32 depressed)
190
{
191
  if( depressed ) return -1; // ignore when button depressed
192
 
193
  return 0; // no error
194
}
195
 
196
static s32 SEQ_UI_Button_Fwd(s32 depressed)
197
{
198
  if( depressed ) return -1; // ignore when button depressed
199
 
200
  return 0; // no error
201
}
202
 
203
static s32 SEQ_UI_Button_F1(s32 depressed)
204
{
205
  if( depressed ) return -1; // ignore when button depressed
206
 
207
  return 0; // no error
208
}
209
 
210
static s32 SEQ_UI_Button_F2(s32 depressed)
211
{
212
  if( depressed ) return -1; // ignore when button depressed
213
 
214
  return 0; // no error
215
}
216
 
217
static s32 SEQ_UI_Button_F3(s32 depressed)
218
{
219
  if( depressed ) return -1; // ignore when button depressed
220
 
221
  return 0; // no error
222
}
223
 
224
static s32 SEQ_UI_Button_F4(s32 depressed)
225
{
226
  if( depressed ) return -1; // ignore when button depressed
227
 
228
  return 0; // no error
229
}
230
 
231
static s32 SEQ_UI_Button_Utility(s32 depressed)
232
{
233
  if( depressed ) return -1; // ignore when button depressed
234
 
235
  return 0; // no error
236
}
237
 
238
static s32 SEQ_UI_Button_Copy(s32 depressed)
239
{
240
  if( depressed ) return -1; // ignore when button depressed
241
 
242
  return 0; // no error
243
}
244
 
245
static s32 SEQ_UI_Button_Paste(s32 depressed)
246
{
247
  if( depressed ) return -1; // ignore when button depressed
248
 
249
  return 0; // no error
250
}
251
 
252
static s32 SEQ_UI_Button_Clear(s32 depressed)
253
{
254
  if( depressed ) return -1; // ignore when button depressed
255
 
256
  return 0; // no error
257
}
258
 
259
static s32 SEQ_UI_Button_Menu(s32 depressed)
260
{
261
  if( depressed ) return -1; // ignore when button depressed
262
 
263
  return 0; // no error
264
}
265
 
266
static s32 SEQ_UI_Button_Select(s32 depressed)
267
{
268
  if( depressed ) return -1; // ignore when button depressed
269
 
270
  return 0; // no error
271
}
272
 
273
static s32 SEQ_UI_Button_Exit(s32 depressed)
274
{
275
  if( depressed ) return -1; // ignore when button depressed
276
 
277
  return 0; // no error
278
}
279
 
280
static s32 SEQ_UI_Button_Edit(s32 depressed)
281
{
282
  if( depressed ) return -1; // ignore when button depressed
283
 
284
  return 0; // no error
285
}
286
 
287
static s32 SEQ_UI_Button_Mute(s32 depressed)
288
{
289
  if( depressed ) return -1; // ignore when button depressed
290
 
291
  return 0; // no error
292
}
293
 
294
static s32 SEQ_UI_Button_Pattern(s32 depressed)
295
{
296
  if( depressed ) return -1; // ignore when button depressed
297
 
298
  return 0; // no error
299
}
300
 
301
static s32 SEQ_UI_Button_Song(s32 depressed)
302
{
303
  if( depressed ) return -1; // ignore when button depressed
304
 
305
  return 0; // no error
306
}
307
 
308
static s32 SEQ_UI_Button_Solo(s32 depressed)
309
{
310
  if( depressed ) return -1; // ignore when button depressed
311
 
312
  return 0; // no error
313
}
314
 
315
static s32 SEQ_UI_Button_Fast(s32 depressed)
316
{
317
  if( depressed ) return -1; // ignore when button depressed
318
 
319
  return 0; // no error
320
}
321
 
322
static s32 SEQ_UI_Button_All(s32 depressed)
323
{
324
  if( depressed ) return -1; // ignore when button depressed
325
 
326
  return 0; // no error
327
}
328
 
329
static s32 SEQ_UI_Button_StepView(s32 depressed)
330
{
331
  if( depressed ) return -1; // ignore when button depressed
332
 
333
  ui_selected_step_view = ui_selected_step_view ? 0 : 1;
334
 
335
  return 0; // no error
336
}
337
 
338
static s32 SEQ_UI_Button_TapTempo(s32 depressed)
339
{
340
  if( depressed ) return -1; // ignore when button depressed
341
 
342
  return 0; // no error
343
}
344
 
345
static s32 SEQ_UI_Button_Track(s32 depressed, u32 track)
346
{
347
  if( depressed ) return -1; // ignore when button depressed
348
 
349
  if( track >= 4 ) return -2; // max. 4 track buttons
350
 
351
  ui_selected_tracks = (1 << track); // TODO: multi-selections!
352
 
353
  return 0; // no error
354
}
355
 
356
static s32 SEQ_UI_Button_Group(s32 depressed, u32 group)
357
{
358
  if( depressed ) return -1; // ignore when button depressed
359
 
360
  if( group >= 4 ) return -2; // max. 4 group buttons
361
 
362
  ui_selected_group = group;
363
 
364
  return 0; // no error
365
}
366
 
367
static s32 SEQ_UI_Button_ParLayer(s32 depressed, u32 par_layer)
368
{
369
  if( depressed ) return -1; // ignore when button depressed
370
 
371
  if( par_layer >= 3 ) return -2; // max. 3 parlayer buttons
372
 
373
  ui_selected_par_layer = par_layer;
374
 
375
  return 0; // no error
376
}
377
 
378
static s32 SEQ_UI_Button_TrgLayer(s32 depressed, u32 trg_layer)
379
{
380
  if( depressed ) return -1; // ignore when button depressed
381
 
382
  if( trg_layer >= 3 ) return -2; // max. 3 trglayer buttons
383
 
384
  ui_selected_trg_layer = trg_layer;
385
 
386
  return 0; // no error
387
}
388
 
389
 
390
 
391
/////////////////////////////////////////////////////////////////////////////
392
// Button handler
393
/////////////////////////////////////////////////////////////////////////////
394
s32 SEQ_UI_Button_Handler(u32 pin, u32 pin_value)
395
{
396
  switch( pin ) {
397
#if BUTTON_GP1
398
    case BUTTON_GP1:   SEQ_UI_Button_GP(pin_value, 0); break;
399
#endif
400
#if BUTTON_GP2
401
    case BUTTON_GP2:   SEQ_UI_Button_GP(pin_value, 1); break;
402
#endif
403
#if BUTTON_GP3
404
    case BUTTON_GP3:   SEQ_UI_Button_GP(pin_value, 2); break;
405
#endif
406
#if BUTTON_GP4
407
    case BUTTON_GP4:   SEQ_UI_Button_GP(pin_value, 3); break;
408
#endif
409
#if BUTTON_GP5
410
    case BUTTON_GP5:   SEQ_UI_Button_GP(pin_value, 4); break;
411
#endif
412
#if BUTTON_GP6
413
    case BUTTON_GP6:   SEQ_UI_Button_GP(pin_value, 5); break;
414
#endif
415
#if BUTTON_GP7
416
    case BUTTON_GP7:   SEQ_UI_Button_GP(pin_value, 6); break;
417
#endif
418
#if BUTTON_GP8
419
    case BUTTON_GP8:   SEQ_UI_Button_GP(pin_value, 7); break;
420
#endif
421
#if BUTTON_GP9
422
    case BUTTON_GP9:   SEQ_UI_Button_GP(pin_value, 8); break;
423
#endif
424
#if BUTTON_GP10
425
    case BUTTON_GP10:  SEQ_UI_Button_GP(pin_value, 9); break;
426
#endif
427
#if BUTTON_GP11
428
    case BUTTON_GP11:  SEQ_UI_Button_GP(pin_value, 10); break;
429
#endif
430
#if BUTTON_GP12
431
    case BUTTON_GP12:  SEQ_UI_Button_GP(pin_value, 11); break;
432
#endif
433
#if BUTTON_GP13
434
    case BUTTON_GP13:  SEQ_UI_Button_GP(pin_value, 12); break;
435
#endif
436
#if BUTTON_GP14
437
    case BUTTON_GP14:  SEQ_UI_Button_GP(pin_value, 13); break;
438
#endif
439
#if BUTTON_GP15
440
    case BUTTON_GP15:  SEQ_UI_Button_GP(pin_value, 14); break;
441
#endif
442
#if BUTTON_GP16
443
    case BUTTON_GP16:  SEQ_UI_Button_GP(pin_value, 15); break;
444
#endif
445
 
446
#if BUTTON_LEFT
447
    case BUTTON_LEFT:  SEQ_UI_Button_Left(pin_value); break;
448
#endif
449
#if BUTTON_RIGHT
450
    case BUTTON_RIGHT: SEQ_UI_Button_Right(pin_value); break;
451
#endif
452
 
453
#if BUTTON_SCRUB
454
    case BUTTON_SCRUB: SEQ_UI_Button_Scrub(pin_value); break;
455
#endif
456
#if BUTTON_METRONOME
457
    case BUTTON_METRONOME: SEQ_UI_Button_Metronome(pin_value); break;
458
#endif
459
 
460
#if BUTTON_STOP
461
    case BUTTON_STOP:  SEQ_UI_Button_Stop(pin_value); break;
462
#endif
463
#if BUTTON_PAUSE
464
    case BUTTON_PAUSE: SEQ_UI_Button_Pause(pin_value); break;
465
#endif
466
#if BUTTON_PLAY
467
    case BUTTON_PLAY:  SEQ_UI_Button_Play(pin_value); break;
468
#endif
469
#if BUTTON_REW
470
    case BUTTON_REW:   SEQ_UI_Button_Rew(pin_value); break;
471
#endif
472
#if BUTTON_FWD
473
    case BUTTON_FWD:   SEQ_UI_Button_Fwd(pin_value); break;
474
#endif
475
 
476
#if BUTTON_F1
477
    case BUTTON_F1:    SEQ_UI_Button_F1(pin_value); break;
478
#endif
479
#if BUTTON_F2
480
    case BUTTON_F2:    SEQ_UI_Button_F2(pin_value); break;
481
#endif
482
#if BUTTON_F3
483
    case BUTTON_F3:    SEQ_UI_Button_F3(pin_value); break;
484
#endif
485
#if BUTTON_F4
486
    case BUTTON_F4:    SEQ_UI_Button_F4(pin_value); break;
487
#endif
488
 
489
#if BUTTON_UTILITY
490
    case BUTTON_UTILITY: SEQ_UI_Button_Utility(pin_value); break;
491
#endif
492
#if BUTTON_COPY
493
    case BUTTON_COPY:  SEQ_UI_Button_Copy(pin_value); break;
494
#endif
495
#if BUTTON_PASTE
496
    case BUTTON_PASTE: SEQ_UI_Button_Paste(pin_value); break;
497
#endif
498
#if BUTTON_CLEAR
499
    case BUTTON_CLEAR: SEQ_UI_Button_Clear(pin_value); break;
500
#endif
501
 
502
#if BUTTON_MENU
503
    case BUTTON_MENU:  SEQ_UI_Button_Menu(pin_value); break;
504
#endif
505
#if BUTTON_SELECT
506
    case BUTTON_SELECT:SEQ_UI_Button_Select(pin_value); break;
507
#endif
508
#if BUTTON_EXIT
509
    case BUTTON_EXIT:  SEQ_UI_Button_Exit(pin_value); break;
510
#endif
511
 
512
#if BUTTON_TRACK1
513
    case BUTTON_TRACK1: SEQ_UI_Button_Track(pin_value, 0); break;
514
#endif
515
#if BUTTON_TRACK2
516
    case BUTTON_TRACK2: SEQ_UI_Button_Track(pin_value, 1); break;
517
#endif
518
#if BUTTON_TRACK3
519
    case BUTTON_TRACK3: SEQ_UI_Button_Track(pin_value, 2); break;
520
#endif
521
#if BUTTON_TRACK4
522
    case BUTTON_TRACK4: SEQ_UI_Button_Track(pin_value, 3); break;
523
#endif
524
 
525
#if BUTTON_PAR_LAYER_A
526
    case BUTTON_PAR_LAYER_A: SEQ_UI_Button_ParLayer(pin_value, 0); break;
527
#endif
528
#if BUTTON_PAR_LAYER_B
529
    case BUTTON_PAR_LAYER_B: SEQ_UI_Button_ParLayer(pin_value, 1); break;
530
#endif
531
#if BUTTON_PAR_LAYER_C
532
    case BUTTON_PAR_LAYER_C: SEQ_UI_Button_ParLayer(pin_value, 2); break;
533
#endif
534
 
535
#if BUTTON_EDIT
536
    case BUTTON_EDIT:   SEQ_UI_Button_Edit(pin_value); break;
537
#endif
538
#if BUTTON_MUTE
539
    case BUTTON_MUTE:   SEQ_UI_Button_Mute(pin_value); break;
540
#endif
541
#if BUTTON_PATTERN
542
    case BUTTON_PATTERN:SEQ_UI_Button_Pattern(pin_value); break;
543
#endif
544
#if BUTTON_SONG
545
    case BUTTON_SONG:   SEQ_UI_Button_Song(pin_value); break;
546
#endif
547
 
548
#if BUTTON_SOLO
549
    case BUTTON_SOLO:   SEQ_UI_Button_Solo(pin_value); break;
550
#endif
551
#if BUTTON_FAST
552
    case BUTTON_FAST:   SEQ_UI_Button_Fast(pin_value); break;
553
#endif
554
#if BUTTON_ALL
555
    case BUTTON_ALL:    SEQ_UI_Button_All(pin_value); break;
556
#endif
557
 
558
#if BUTTON_GROUP1
559
    case BUTTON_GROUP1: SEQ_UI_Button_Group(pin_value, 0); break;
560
#endif
561
#if BUTTON_GROUP2
562
    case BUTTON_GROUP2: SEQ_UI_Button_Group(pin_value, 1); break;
563
#endif
564
#if BUTTON_GROUP3
565
    case BUTTON_GROUP3: SEQ_UI_Button_Group(pin_value, 2); break;
566
#endif
567
#if BUTTON_GROUP4
568
    case BUTTON_GROUP4: SEQ_UI_Button_Group(pin_value, 3); break;
569
#endif
570
 
571
#if BUTTON_TRG_LAYER_A
572
    case BUTTON_TRG_LAYER_A: SEQ_UI_Button_TrgLayer(pin_value, 0); break;
573
#endif
574
#if BUTTON_TRG_LAYER_B
575
    case BUTTON_TRG_LAYER_B: SEQ_UI_Button_TrgLayer(pin_value, 1); break;
576
#endif
577
#if BUTTON_TRG_LAYER_C
578
    case BUTTON_TRG_LAYER_C: SEQ_UI_Button_TrgLayer(pin_value, 2); break;
579
#endif
580
 
581
#if BUTTON_STEP_VIEW
582
    case BUTTON_STEP_VIEW: SEQ_UI_Button_StepView(pin_value); break;
583
#endif
584
 
585
#if BUTTON_TAP_TEMPO
586
    case BUTTON_TAP_TEMPO:   SEQ_UI_Button_TapTempo(pin_value); break;
587
#endif
588
 
589
    default:
590
      return -1; // button function not mapped to physical button
591
  }
592
 
593
  // request display update
159 tk 594
  seq_ui_display_update_req = 1;
134 tk 595
 
596
  return 0; // no error
597
}
598
 
599
 
600
/////////////////////////////////////////////////////////////////////////////
601
// Encoder handler
602
/////////////////////////////////////////////////////////////////////////////
603
s32 SEQ_UI_Encoder_Handler(u32 encoder, s32 incrementer)
604
{
605
  if( encoder > 16 )
606
    return -1; // encoder doesn't exist
607
 
608
  // limit incrementer
609
  if( incrementer > 3 )
610
    incrementer = 3;
611
  else if( incrementer < -3 )
612
    incrementer = -3;
613
 
614
  if( encoder == 0 ) {
615
    s32 value = played_step + incrementer;
616
    if( value < 0 )
617
      value = 0;
618
    if( value > SEQ_CORE_NUM_STEPS-1 )
619
      value = SEQ_CORE_NUM_STEPS-1;
620
    played_step = (u8)value;
621
  } else {
622
    u8 visible_track = SEQ_UI_VisibleTrackGet();
623
    u8 step = encoder-1 + ui_selected_step_view*16;
624
 
625
    // select step
626
    ui_selected_step = step;
627
 
628
    // add to absolute value
629
    s32 value = (s32)par_layer_value[visible_track][ui_selected_par_layer][step] + incrementer;
630
    if( value < 0 )
631
      value = 0;
632
    else if( value >= 128 )
633
      value = 127;
634
 
635
    // take over if changed
636
    if( (u8)value != par_layer_value[visible_track][ui_selected_par_layer][step] ) {
637
      par_layer_value[visible_track][ui_selected_par_layer][step] = (u8)value;
638
      // here we could do more on changes - important for mixer function (event only sent on changes)
639
    }
640
 
641
    // (de)activate gate depending on value
642
    if( value )
643
      trg_layer_value[visible_track][0][step>>3] |= (1 << (step&7));
644
    else
645
      trg_layer_value[visible_track][0][step>>3] &= ~(1 << (step&7));
646
  }
647
 
648
  // request display update
159 tk 649
  seq_ui_display_update_req = 1;
134 tk 650
 
651
  return 0; // no error
652
}
653
 
654
 
655
/////////////////////////////////////////////////////////////////////////////
656
// Update LCD messages
657
// Usually called from background task
658
/////////////////////////////////////////////////////////////////////////////
659
s32 SEQ_UI_LCD_Handler(void)
660
{
159 tk 661
  if( seq_ui_display_init_req ) {
662
    seq_ui_display_init_req = 0; // clear request
134 tk 663
 
664
    // clear both LCDs
665
    int i;
666
    for(i=0; i<2; ++i) {
667
      MIOS32_LCD_DeviceSet(i);
668
      SEQ_LCD_Clear();
669
    }
670
 
671
    // initialise charset
672
    SEQ_LCD_InitSpecialChars(SEQ_LCD_CHARSET_VBARS);
673
 
674
    // request display update
159 tk 675
    seq_ui_display_update_req = 1;
134 tk 676
  }
677
 
159 tk 678
  if( seq_ui_display_update_req ) {
679
    seq_ui_display_update_req = 0; // clear request
134 tk 680
 
681
    char tmp[128];
682
    u8 step;
683
    u8 visible_track = SEQ_UI_VisibleTrackGet();
684
 
685
    ///////////////////////////////////////////////////////////////////////////
686
    MIOS32_LCD_DeviceSet(0);
687
    MIOS32_LCD_CursorSet(0, 0);
688
 
689
    SEQ_LCD_PrintGxTy(ui_selected_group, ui_selected_tracks);
690
    SEQ_LCD_PrintSpaces(2);
691
 
692
    SEQ_LCD_PrintParLayer(ui_selected_par_layer);
693
    SEQ_LCD_PrintSpaces(1);
694
 
695
    MIOS32_LCD_PrintFormattedString("Chn%2d", midi_channel+1);
696
    MIOS32_LCD_PrintChar('/');
697
    SEQ_LCD_PrintMIDIPort(midi_port);
698
    SEQ_LCD_PrintSpaces(1);
699
 
700
    SEQ_LCD_PrintTrgLayer(ui_selected_trg_layer);
701
 
702
    SEQ_LCD_PrintStepView(ui_selected_step_view);
703
 
704
 
705
    ///////////////////////////////////////////////////////////////////////////
706
    MIOS32_LCD_DeviceSet(1);
707
    MIOS32_LCD_CursorSet(0, 0);
708
 
709
    MIOS32_LCD_PrintFormattedString("Step");
710
    SEQ_LCD_PrintSelectedStep(ui_selected_step, 15);
711
    MIOS32_LCD_PrintChar(':');
712
 
713
    SEQ_LCD_PrintNote(par_layer_value[visible_track][0][ui_selected_step]);
714
    MIOS32_LCD_PrintChar((char)par_layer_value[visible_track][1][ui_selected_step] >> 4);
715
    SEQ_LCD_PrintSpaces(1);
716
 
717
    MIOS32_LCD_PrintFormattedString("Vel:%3d", par_layer_value[visible_track][1][ui_selected_step]);
718
    SEQ_LCD_PrintSpaces(1);
719
 
720
    MIOS32_LCD_PrintFormattedString("Len:");
721
    SEQ_LCD_PrintGatelength(par_layer_value[visible_track][2][ui_selected_step]);
722
    SEQ_LCD_PrintSpaces(1);
723
 
724
    MIOS32_LCD_PrintFormattedString("G-a-r--");
725
 
726
    ///////////////////////////////////////////////////////////////////////////
727
    MIOS32_LCD_DeviceSet(0);
728
    MIOS32_LCD_CursorSet(0, 1);
729
 
730
    for(step=0; step<16; ++step) {
731
      // 9th step reached: switch to second LCD
732
      if( step == 8 ) {
733
        MIOS32_LCD_DeviceSet(1);
734
        MIOS32_LCD_CursorSet(0, 1);
735
      }
736
 
737
      u8 visible_step = step + 16*ui_selected_step_view;
738
      u8 note = par_layer_value[visible_track][0][visible_step];
739
      u8 vel = par_layer_value[visible_track][1][visible_step];
740
      u8 len = par_layer_value[visible_track][2][visible_step];
741
      u8 gate = trg_layer_value[visible_track][0][visible_step>>3] & (1 << (visible_step&7));
742
 
743
      switch( ui_selected_par_layer ) {
744
        case 0: // Note
745
        case 1: // Velocity
746
 
747
    if( gate ) {
748
      SEQ_LCD_PrintNote(note);
749
      MIOS32_LCD_PrintChar((char)vel >> 4);
750
    } else {
751
      MIOS32_LCD_PrintFormattedString("----");
752
    }
753
    break;
754
 
755
        case 2: // Gatelength
756
      // TODO: print length like on real hardware (length bars)
757
      SEQ_LCD_PrintGatelength(len);
758
      break;
759
        default:
760
      MIOS32_LCD_PrintFormattedString("????");
761
      }
762
 
763
      MIOS32_LCD_PrintChar(
764
          (visible_step == ui_selected_step) ? '<'
765
    : ((visible_step == ui_selected_step-1) ? '>' : ' '));
766
    }
767
  }
768
 
159 tk 769
 
770
 
771
  // for debugging
772
#if 0
773
  MIOS32_LCD_DeviceSet(0);
774
  MIOS32_LCD_CursorSet(0, 0);
775
  MIOS32_LCD_PrintFormattedString("%5d  ", seq_midi_queue_size);
776
#endif
777
 
134 tk 778
  return 0; // no error
779
}
780
 
781
 
782
 
783
/////////////////////////////////////////////////////////////////////////////
784
// Update all LEDs
785
// Usually called from background task
786
/////////////////////////////////////////////////////////////////////////////
787
s32 SEQ_UI_LED_Handler(void)
788
{
789
  u8 visible_track = SEQ_UI_VisibleTrackGet();
790
 
791
  // track LEDs
792
  SEQ_LED_PinSet(LED_TRACK1, (ui_selected_tracks & (1 << 0)) ? 1 : 0);
793
  SEQ_LED_PinSet(LED_TRACK2, (ui_selected_tracks & (1 << 1)) ? 1 : 0);
794
  SEQ_LED_PinSet(LED_TRACK3, (ui_selected_tracks & (1 << 2)) ? 1 : 0);
795
  SEQ_LED_PinSet(LED_TRACK4, (ui_selected_tracks & (1 << 3)) ? 1 : 0);
796
 
797
  // parameter layer LEDs
798
  SEQ_LED_PinSet(LED_PAR_LAYER_A, (ui_selected_par_layer == 0) ? 1 : 0);
799
  SEQ_LED_PinSet(LED_PAR_LAYER_B, (ui_selected_par_layer == 1) ? 1 : 0);
800
  SEQ_LED_PinSet(LED_PAR_LAYER_C, (ui_selected_par_layer == 2) ? 1 : 0);
801
 
802
  // group LEDs
803
  SEQ_LED_PinSet(LED_GROUP1, (ui_selected_group == 0) ? 1 : 0);
804
  SEQ_LED_PinSet(LED_GROUP2, (ui_selected_group == 1) ? 1 : 0);
805
  SEQ_LED_PinSet(LED_GROUP3, (ui_selected_group == 2) ? 1 : 0);
806
  SEQ_LED_PinSet(LED_GROUP4, (ui_selected_group == 3) ? 1 : 0);
807
 
808
  // trigger layer LEDs
809
  SEQ_LED_PinSet(LED_TRG_LAYER_A, (ui_selected_trg_layer == 0) ? 1 : 0);
810
  SEQ_LED_PinSet(LED_TRG_LAYER_B, (ui_selected_trg_layer == 1) ? 1 : 0);
811
  SEQ_LED_PinSet(LED_TRG_LAYER_C, (ui_selected_trg_layer == 2) ? 1 : 0);
812
 
813
  // remaining LEDs
814
  SEQ_LED_PinSet(LED_EDIT, 1);
815
  SEQ_LED_PinSet(LED_MUTE, 0);
816
  SEQ_LED_PinSet(LED_PATTERN, 0);
817
  SEQ_LED_PinSet(LED_SONG, 0);
818
 
819
  SEQ_LED_PinSet(LED_SOLO, 0);
820
  SEQ_LED_PinSet(LED_FAST, 0);
821
  SEQ_LED_PinSet(LED_ALL, 0);
822
 
159 tk 823
  SEQ_LED_PinSet(LED_PLAY, seq_core_state_run);
824
  SEQ_LED_PinSet(LED_STOP, !seq_core_state_run);
825
  SEQ_LED_PinSet(LED_PAUSE, seq_core_state_pause);
134 tk 826
 
827
  SEQ_LED_PinSet(LED_STEP_1_16, (ui_selected_step_view == 0) ? 1 : 0);
828
  SEQ_LED_PinSet(LED_STEP_17_32, (ui_selected_step_view == 1) ? 1 : 0); // will be obsolete in MBSEQ V4
829
 
830
  // write GP LED values into ui_gp_leds variable
831
  // will be transfered to DOUT registers in SEQ_UI_LED_Handler_Periodic
832
  ui_gp_leds =
833
    (trg_layer_value[visible_track][ui_selected_trg_layer][2*ui_selected_step_view+1] << 8) |
834
     trg_layer_value[visible_track][ui_selected_trg_layer][2*ui_selected_step_view+0];
835
 
836
  return 0; // no error
837
}
838
 
839
 
840
/////////////////////////////////////////////////////////////////////////////
841
// updates high-prio LED functions (GP LEDs and Beat LED)
842
// Called before SRIO update
843
/////////////////////////////////////////////////////////////////////////////
844
s32 SEQ_UI_LED_Handler_Periodic()
845
{
846
  // GP LEDs are only updated when ui_gp_leds or pos_marker_mask has changed
847
  static u16 prev_ui_gp_leds = 0x0000;
848
  static u16 prev_pos_marker_mask = 0x0000;
849
 
850
 
851
  // beat LED: tmp. for demo w/o real sequencer
852
  SEQ_LED_PinSet(LED_BEAT, ((played_step & 3) == 0) ? 1 : 0);
853
 
854
  // for song position marker (supports 16 LEDs, check for selected step view)
855
  u16 pos_marker_mask = 0x0000;
856
  if( (played_step >> 4) == ui_selected_step_view )
857
    pos_marker_mask = 1 << (played_step & 0xf);
858
 
859
  // exit of pattern hasn't changed
860
  if( prev_ui_gp_leds == ui_gp_leds && prev_pos_marker_mask == pos_marker_mask )
861
    return 0;
862
  prev_ui_gp_leds = ui_gp_leds;
863
  prev_pos_marker_mask = pos_marker_mask;
864
 
865
  // transfer to GP LEDs
866
 
867
#ifdef DEFAULT_GP_DOUT_SR_L
868
# ifdef DEFAULT_GP_DOUT_SR_L2
869
  SEQ_LED_SRSet(DEFAULT_GP_DOUT_SR_L-1, (ui_gp_leds >> 0) & 0xff);
870
# else
871
  SEQ_LED_SRSet(DEFAULT_GP_DOUT_SR_L-1, ((ui_gp_leds ^ pos_marker_mask) >> 0) & 0xff);
872
# endif
873
#endif
874
#ifdef DEFAULT_GP_DOUT_SR_R
875
# ifdef DEFAULT_GP_DOUT_SR_R2
876
  SEQ_LED_SRSet(DEFAULT_GP_DOUT_SR_R-1, (ui_gp_leds >> 8) & 0xff);
877
#else
878
  SEQ_LED_SRSet(DEFAULT_GP_DOUT_SR_R-1, ((ui_gp_leds ^ pos_marker_mask) >> 8) & 0xff);
879
#endif
880
#endif
881
 
882
#ifdef DEFAULT_GP_DOUT_SR_L2
883
  SEQ_LED_SRSet(DEFAULT_GP_DOUT_SR_L2-1, (pos_marker_mask >> 0) & 0xff);
884
#endif
885
#ifdef DEFAULT_GP_DOUT_SR_R2
886
  SEQ_LED_SRSet(DEFAULT_GP_DOUT_SR_R2-1, (pos_marker_mask >> 8) & 0xff);
887
#endif
888
 
889
#if DEFAULT_SRM_ENABLED && DEFAULT_SRM_DOUT_M_MAPPING == 1
890
  // for wilba's frontpanel
891
 
892
  // BLM8X8 DOUT -> GP LED mapping
893
  // 0 = 15,16  1 = 13,14   2 = 11,12   3 = 9,10
894
  // 4 = 1,2    5 = 3,4     6 = 5,6     7 = 7,8
895
 
896
  // bit 7: first green (i.e. GP1-G)
897
  // bit 6: first red (i.e. GP1-R)
898
  // bit 5: second green (i.e. GP2-G)
899
  // bit 4: second red (i.e. GP2-R)
900
 
901
  // this mapping routine takes ca. 5 uS
902
  // since it's only executed when ui_gp_leds or gp_mask has changed, it doesn't really hurt
903
 
904
  u16 modified_gp_leds = ui_gp_leds;
905
#if 1
906
  // extra: red LED is lit exclusively for higher contrast
907
  modified_gp_leds &= ~pos_marker_mask;
908
#endif
909
 
910
  int sr;
911
  const u8 blm8x8_sr_map[8] = {4, 5, 6, 7, 3, 2, 1, 0};
912
  u16 gp_mask = 1 << 0;
913
  for(sr=0; sr<8; ++sr) {
914
    u8 pattern = 0;
915
 
916
    if( modified_gp_leds & gp_mask )
917
      pattern |= 0x80;
918
    if( pos_marker_mask & gp_mask )
919
      pattern |= 0x40;
920
    gp_mask <<= 1;
921
    if( modified_gp_leds & gp_mask )
922
      pattern |= 0x20;
923
    if( pos_marker_mask & gp_mask )
924
      pattern |= 0x10;
925
    gp_mask <<= 1;
926
 
927
    u8 mapped_sr = blm8x8_sr_map[sr];
928
    blm8x8_led_row[mapped_sr] = (blm8x8_led_row[mapped_sr] & 0x0f) | pattern;
929
  }
930
#endif
931
 
932
}
933
 
934
 
935
/////////////////////////////////////////////////////////////////////////////
936
// Returns the currently visible track
937
/////////////////////////////////////////////////////////////////////////////
938
u8 SEQ_UI_VisibleTrackGet(void)
939
{
940
  u8 offset = 0;
941
 
942
  if( ui_selected_tracks & (1 << 3) )
943
    offset = 3;
944
  if( ui_selected_tracks & (1 << 2) )
945
    offset = 2;
946
  if( ui_selected_tracks & (1 << 1) )
947
    offset = 1;
948
  if( ui_selected_tracks & (1 << 0) )
949
    offset = 0;
950
 
951
  return 4*ui_selected_group + offset;
952
}
953