BaseMachine UI Controllerに分離

Dependencies:   AverageAnalogIn PinDetect RotaryEncoder Sequence SequencerDisplay mbed-rtos mbed st7567LCD BaseMachineComon

Fork of BaseMachine_Sequencer by Ryo Od

Committer:
ryood
Date:
Sun Oct 23 05:48:57 2016 +0000
Revision:
54:38187ac44253
Parent:
53:cad31fd61d8a
Child:
55:ab24d74eb0e6
Add a slave reset sequence at init.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
ryood 15:9813d8eaf57e 1 /*
ryood 15:9813d8eaf57e 2 * main.cpp
ryood 15:9813d8eaf57e 3 * SpiSequencerSender_test
ryood 15:9813d8eaf57e 4 *
ryood 38:cafa2fff5565 5 * 2016.10.02 UI Controllerに分割
ryood 15:9813d8eaf57e 6 * 2016.08.20 mbed Rev 121 / mbed-rtos Rev 117で動作確認
ryood 15:9813d8eaf57e 7 *
ryood 15:9813d8eaf57e 8 */
ryood 15:9813d8eaf57e 9
ryood 0:21e39bc75e31 10 #include "mbed.h"
ryood 5:4abac408b827 11 #include "rtos.h"
ryood 16:b0419e3c9079 12 #include "st7565LCD.h"
ryood 18:309f794eba74 13 #include "PinDetect.h"
ryood 20:00d3b6ace8c7 14 #include "RotaryEncoder.h"
ryood 19:241a4b355413 15 #include "AverageAnalogIn.h"
ryood 0:21e39bc75e31 16
ryood 38:cafa2fff5565 17 #define UART_TRACE (1)
ryood 53:cad31fd61d8a 18 #include "BaseMachineCommon.h"
ryood 38:cafa2fff5565 19 #include "Sequence.h"
ryood 17:557658db3e81 20 #include "ST7565_SequencerDisplay.h"
ryood 0:21e39bc75e31 21
ryood 38:cafa2fff5565 22 #define TITLE_STR1 ("BaseMachine UI Controller")
ryood 53:cad31fd61d8a 23 #define TITLE_STR2 ("20161023")
ryood 16:b0419e3c9079 24
ryood 38:cafa2fff5565 25 #define SPI2_RATE (1000000)
ryood 47:f4c16d1e4207 26 #define POT_RESOLUTION (7) // bit
ryood 53:cad31fd61d8a 27 #define AIN_AVERAGE (16) // AnalogInを移動平均する要素数
ryood 53:cad31fd61d8a 28 #define POLLING_POTS_WAIT (20) // POT読み取りThreadのWait値(ミリ秒)
ryood 0:21e39bc75e31 29
ryood 20:00d3b6ace8c7 30 const int bpmMax = 240;
ryood 20:00d3b6ace8c7 31 const int bpmMin = 60;
ryood 40:2f9616bdcf65 32 const int octaveMax = 2;
ryood 40:2f9616bdcf65 33 const int octaveMin = -2;
ryood 38:cafa2fff5565 34 const int waveShapeMax = 1;
ryood 28:d8614d2b82f9 35 const int UImodeMax = 2;
ryood 14:c173e03ee3ad 36
ryood 16:b0419e3c9079 37 // Devices
ryood 16:b0419e3c9079 38 //
ryood 53:cad31fd61d8a 39
ryood 53:cad31fd61d8a 40 //RESET Line
ryood 53:cad31fd61d8a 41 //DigitalOut ResetLine();
ryood 53:cad31fd61d8a 42
ryood 16:b0419e3c9079 43 //SPI (PinName mosi, PinName miso, PinName sclk, PinName ssel=NC)
ryood 41:48864f5f5424 44 SPI SpiMaster(PA_7, PA_6, PA_5);
ryood 41:48864f5f5424 45 DigitalOut SpiMasterCs(PB_6);
ryood 53:cad31fd61d8a 46 InterruptIn StepChangeInterrupt(PC_7);
ryood 54:38187ac44253 47 DigitalOut SlaveReset(PB_9);
ryood 16:b0419e3c9079 48
ryood 16:b0419e3c9079 49 //ST7565(PinName mosi, PinName sclk, PinName cs, PinName rst, PinName a0);
ryood 16:b0419e3c9079 50 ST7565 gLCD(PB_15, PB_13, PB_12, PB_2, PB_1);
ryood 16:b0419e3c9079 51
ryood 42:3c71f925a47b 52 AverageAnalogIn AinPulseWidth(PC_2, AIN_AVERAGE);
ryood 42:3c71f925a47b 53 AverageAnalogIn AinCutOff(PB_0, AIN_AVERAGE);
ryood 42:3c71f925a47b 54 AverageAnalogIn AinResonance(PC_1, AIN_AVERAGE);
ryood 42:3c71f925a47b 55 AverageAnalogIn AinLevel(PC_0, AIN_AVERAGE);
ryood 42:3c71f925a47b 56 AverageAnalogIn AinDuration(PA_4, AIN_AVERAGE);
ryood 42:3c71f925a47b 57 AverageAnalogIn AinDecay(PA_1, AIN_AVERAGE);
ryood 42:3c71f925a47b 58 AverageAnalogIn AinSustain(PA_0, AIN_AVERAGE);
ryood 42:3c71f925a47b 59 AverageAnalogIn AinAccentLevel(PC_3, AIN_AVERAGE);
ryood 10:fb04f9959fd9 60
ryood 52:72332a596bc5 61 RotaryEncoder RotEncStep(PA_11, PA_12, 0, SEQUENCE_N - 1, 0);
ryood 26:fbf48a178aeb 62 RotaryEncoder RotEncPitch(PB_5, PB_4, 0, Sequence::getMaxPitch() - 1, 0);
ryood 31:16d1fbf3a167 63 RotaryEncoder RotEncBpm(PC_12, PC_10, bpmMin, bpmMax, 120);
ryood 20:00d3b6ace8c7 64
ryood 18:309f794eba74 65 PinDetect PinWaveShape(PD_2, PullUp);
ryood 28:d8614d2b82f9 66 PinDetect PinUIMode(PC_11, PullUp);
ryood 31:16d1fbf3a167 67 PinDetect PinOctaveUp(PB_3, PullUp);
ryood 31:16d1fbf3a167 68 PinDetect PinOctaveDown(PA_10, PullUp);
ryood 31:16d1fbf3a167 69 PinDetect PinNoteOnOff(PC_5, PullUp);
ryood 31:16d1fbf3a167 70 PinDetect PinTie(PC_6, PullUp);
ryood 31:16d1fbf3a167 71 PinDetect PinAccent(PC_8, PullUp);
ryood 52:72332a596bc5 72 PinDetect PinRunStop(PC_9, PullUp);
ryood 18:309f794eba74 73
ryood 16:b0419e3c9079 74 // Grobal Variables
ryood 16:b0419e3c9079 75 //
ryood 16:b0419e3c9079 76 Sequence sequences[SEQUENCE_N];
ryood 17:557658db3e81 77 ST7565_SequencerDisplay sequencerDisplay(&gLCD, sequences, SEQUENCE_N);
ryood 17:557658db3e81 78
ryood 38:cafa2fff5565 79 struct OscillatorParam {
ryood 38:cafa2fff5565 80 uint8_t waveShape;
ryood 38:cafa2fff5565 81 uint8_t pulseWidth;
ryood 38:cafa2fff5565 82 } oscillatorParam;
ryood 38:cafa2fff5565 83
ryood 38:cafa2fff5565 84 struct FilterParam {
ryood 38:cafa2fff5565 85 uint8_t cutoff;
ryood 38:cafa2fff5565 86 uint8_t resonance;
ryood 38:cafa2fff5565 87 } filterParam;
ryood 38:cafa2fff5565 88
ryood 38:cafa2fff5565 89 struct EnvelopeParam {
ryood 43:12d11507c077 90 uint8_t level;
ryood 43:12d11507c077 91 uint8_t length;
ryood 43:12d11507c077 92 uint8_t duration;
ryood 43:12d11507c077 93 uint8_t decay;
ryood 43:12d11507c077 94 uint8_t sustain;
ryood 38:cafa2fff5565 95 } envelopeParam;
ryood 38:cafa2fff5565 96
ryood 38:cafa2fff5565 97 uint8_t bpm = 120;
ryood 38:cafa2fff5565 98 uint8_t accentLevel = 127;
ryood 38:cafa2fff5565 99
ryood 38:cafa2fff5565 100 int currentStep = 0;
ryood 38:cafa2fff5565 101 int playingStep = 0;
ryood 38:cafa2fff5565 102 bool isRunning = false;
ryood 38:cafa2fff5565 103 bool isDirty = true;
ryood 38:cafa2fff5565 104 int UImode = 0;
ryood 38:cafa2fff5565 105
ryood 38:cafa2fff5565 106 volatile bool isStepChanged = false;
ryood 16:b0419e3c9079 107 volatile uint8_t pinFlag = 0x00;
ryood 16:b0419e3c9079 108
ryood 16:b0419e3c9079 109 enum PinBit {
ryood 16:b0419e3c9079 110 bWaveShape = 0x01,
ryood 38:cafa2fff5565 111 bUIMode = 0x02,
ryood 16:b0419e3c9079 112 bOctaveUp = 0x04,
ryood 16:b0419e3c9079 113 bOctaveDown = 0x08,
ryood 16:b0419e3c9079 114 bNoteOnOff = 0x10,
ryood 16:b0419e3c9079 115 bTie = 0x20,
ryood 16:b0419e3c9079 116 bAccent = 0x40,
ryood 16:b0419e3c9079 117 bRunStop = 0x80
ryood 16:b0419e3c9079 118 };
ryood 16:b0419e3c9079 119
ryood 16:b0419e3c9079 120 //------------------------------------------------------------------------
ryood 38:cafa2fff5565 121 // InterruptIn ISR
ryood 16:b0419e3c9079 122 //------------------------------------------------------------------------
ryood 38:cafa2fff5565 123 void updateStep()
ryood 8:de409197ff95 124 {
ryood 38:cafa2fff5565 125 isStepChanged = true;
ryood 8:de409197ff95 126 }
ryood 8:de409197ff95 127
ryood 16:b0419e3c9079 128 //------------------------------------------------------------------------
ryood 18:309f794eba74 129 // PinDetect ISR
ryood 18:309f794eba74 130 //------------------------------------------------------------------------
ryood 18:309f794eba74 131 void swWaveShapePressed()
ryood 18:309f794eba74 132 {
ryood 18:309f794eba74 133 pinFlag |= bWaveShape;
ryood 18:309f794eba74 134 }
ryood 18:309f794eba74 135
ryood 28:d8614d2b82f9 136 void swUIModePressed()
ryood 18:309f794eba74 137 {
ryood 28:d8614d2b82f9 138 pinFlag |= bUIMode;
ryood 18:309f794eba74 139 }
ryood 18:309f794eba74 140
ryood 18:309f794eba74 141 void swOctaveUpPressed()
ryood 18:309f794eba74 142 {
ryood 18:309f794eba74 143 pinFlag |= bOctaveUp;
ryood 18:309f794eba74 144 }
ryood 18:309f794eba74 145
ryood 18:309f794eba74 146 void swOctaveDownPressed()
ryood 18:309f794eba74 147 {
ryood 18:309f794eba74 148 pinFlag |= bOctaveDown;
ryood 18:309f794eba74 149 }
ryood 18:309f794eba74 150
ryood 18:309f794eba74 151 void swNoteOnOffPressed()
ryood 18:309f794eba74 152 {
ryood 18:309f794eba74 153 pinFlag |= bNoteOnOff;
ryood 18:309f794eba74 154 }
ryood 18:309f794eba74 155
ryood 18:309f794eba74 156 void swTiePressed()
ryood 18:309f794eba74 157 {
ryood 18:309f794eba74 158 pinFlag |= bTie;
ryood 18:309f794eba74 159 }
ryood 18:309f794eba74 160
ryood 18:309f794eba74 161 void swAccentPressed()
ryood 18:309f794eba74 162 {
ryood 18:309f794eba74 163 pinFlag |= bAccent;
ryood 18:309f794eba74 164 }
ryood 18:309f794eba74 165
ryood 18:309f794eba74 166 void swRunStopPressed()
ryood 18:309f794eba74 167 {
ryood 18:309f794eba74 168 pinFlag |= bRunStop;
ryood 18:309f794eba74 169 }
ryood 18:309f794eba74 170
ryood 18:309f794eba74 171 //------------------------------------------------------------------------
ryood 16:b0419e3c9079 172 // Functions
ryood 16:b0419e3c9079 173 //------------------------------------------------------------------------
ryood 49:22e651444533 174 uint8_t getNoteData(uint8_t step)
ryood 49:22e651444533 175 {
ryood 49:22e651444533 176 uint8_t noteData = 0;
ryood 49:22e651444533 177
ryood 49:22e651444533 178 noteData |= (step << 4);
ryood 49:22e651444533 179 noteData |= (sequences[step].isAccent() ? 4 : 0);
ryood 49:22e651444533 180 noteData |= (sequences[step].isTie() ? 2 : 0);
ryood 49:22e651444533 181 noteData |= (sequences[step].isNoteOn() ? 1 : 0);
ryood 49:22e651444533 182
ryood 49:22e651444533 183 return noteData;
ryood 49:22e651444533 184 }
ryood 49:22e651444533 185
ryood 44:b1bdccdbf67e 186 uint16_t SpiSendParams(uint8_t cmd, uint8_t data)
ryood 44:b1bdccdbf67e 187 {
ryood 44:b1bdccdbf67e 188 uint16_t sendVal = ((uint16_t)cmd << 8) | data;
ryood 44:b1bdccdbf67e 189
ryood 44:b1bdccdbf67e 190 SpiMasterCs = 0;
ryood 44:b1bdccdbf67e 191 uint16_t recievedVal = SpiMaster.write(sendVal);
ryood 44:b1bdccdbf67e 192 SpiMasterCs = 1;
ryood 44:b1bdccdbf67e 193 //Thread::wait(1);
ryood 44:b1bdccdbf67e 194
ryood 44:b1bdccdbf67e 195 return recievedVal;
ryood 44:b1bdccdbf67e 196 }
ryood 44:b1bdccdbf67e 197
ryood 49:22e651444533 198 uint16_t SpiSendAllParams()
ryood 45:3c7143da38d1 199 {
ryood 49:22e651444533 200 SpiSendParams(CMD_BPM, bpm);
ryood 49:22e651444533 201 SpiSendParams(CMD_ACCENT_LEVEL, accentLevel);
ryood 49:22e651444533 202 SpiSendParams(CMD_WAVE_SHAPE , oscillatorParam.waveShape);
ryood 49:22e651444533 203 SpiSendParams(CMD_PULSE_WIDTH, oscillatorParam.pulseWidth);
ryood 49:22e651444533 204 SpiSendParams(CMD_CUTOFF, filterParam.cutoff);
ryood 49:22e651444533 205 SpiSendParams(CMD_RESONANCE, filterParam.resonance);
ryood 49:22e651444533 206 SpiSendParams(CMD_LEVEL, envelopeParam.level);
ryood 49:22e651444533 207 SpiSendParams(CMD_DURATION, envelopeParam.duration);
ryood 49:22e651444533 208 SpiSendParams(CMD_DECAY, envelopeParam.decay);
ryood 49:22e651444533 209 SpiSendParams(CMD_SUSTAIN, envelopeParam.sustain);
ryood 49:22e651444533 210
ryood 49:22e651444533 211 for (int i = 0; i < SEQUENCE_N; i++) {
ryood 49:22e651444533 212 SpiSendParams(CMD_NOTE, getNoteData(i));
ryood 49:22e651444533 213 SpiSendParams(CMD_PITCH, sequences[i].getPitch());
ryood 49:22e651444533 214 }
ryood 49:22e651444533 215
ryood 49:22e651444533 216 uint16_t retVal = SpiSendParams(CMD_RCV_PLAYING_STEP, 0xaa); // Send dummy data
ryood 45:3c7143da38d1 217
ryood 49:22e651444533 218 return retVal;
ryood 45:3c7143da38d1 219 }
ryood 45:3c7143da38d1 220
ryood 20:00d3b6ace8c7 221 void pollingRotEncs()
ryood 20:00d3b6ace8c7 222 {
ryood 20:00d3b6ace8c7 223 int _bpm = RotEncBpm.getVal();
ryood 38:cafa2fff5565 224 if (_bpm != bpm) {
ryood 38:cafa2fff5565 225 bpm = _bpm;
ryood 25:7382bc0a0329 226 sequencerDisplay.setBpm(_bpm);
ryood 46:0fb579ecdd77 227 SpiSendParams(CMD_BPM, _bpm);
ryood 20:00d3b6ace8c7 228 isDirty = true;
ryood 20:00d3b6ace8c7 229 }
ryood 20:00d3b6ace8c7 230
ryood 20:00d3b6ace8c7 231 int _step = RotEncStep.getVal();
ryood 20:00d3b6ace8c7 232 if (_step != currentStep) {
ryood 20:00d3b6ace8c7 233 currentStep = _step;
ryood 20:00d3b6ace8c7 234 // syncronize sequence value & Rotary Encoder's value
ryood 20:00d3b6ace8c7 235 RotEncPitch.setVal(sequences[currentStep].getPitch());
ryood 46:0fb579ecdd77 236 SpiSendParams(CMD_NOTE, getNoteData(_step));
ryood 46:0fb579ecdd77 237 SpiSendParams(CMD_PITCH, sequences[_step].getPitch());
ryood 20:00d3b6ace8c7 238 isDirty = true;
ryood 20:00d3b6ace8c7 239 }
ryood 20:00d3b6ace8c7 240
ryood 20:00d3b6ace8c7 241 int _pitch = RotEncPitch.getVal();
ryood 20:00d3b6ace8c7 242 if (_pitch != sequences[currentStep].getPitch()) {
ryood 20:00d3b6ace8c7 243 sequences[currentStep].setPitch(_pitch);
ryood 46:0fb579ecdd77 244 SpiSendParams(CMD_NOTE, getNoteData(currentStep));
ryood 46:0fb579ecdd77 245 SpiSendParams(CMD_PITCH, _pitch);
ryood 20:00d3b6ace8c7 246 isDirty = true;
ryood 20:00d3b6ace8c7 247 }
ryood 19:241a4b355413 248 }
ryood 19:241a4b355413 249
ryood 18:309f794eba74 250 void pollingPins()
ryood 18:309f794eba74 251 {
ryood 18:309f794eba74 252 if (pinFlag & bWaveShape) {
ryood 18:309f794eba74 253 #if (UART_TRACE)
ryood 18:309f794eba74 254 printf("PinWaveShape Pushed\r\n");
ryood 18:309f794eba74 255 #endif
ryood 38:cafa2fff5565 256 uint8_t _waveShape = oscillatorParam.waveShape;
ryood 38:cafa2fff5565 257 _waveShape++;
ryood 40:2f9616bdcf65 258 if (_waveShape > waveShapeMax) {
ryood 38:cafa2fff5565 259 _waveShape = 0;
ryood 18:309f794eba74 260 }
ryood 38:cafa2fff5565 261 oscillatorParam.waveShape = _waveShape;
ryood 38:cafa2fff5565 262 sequencerDisplay.setWaveShape(_waveShape);
ryood 18:309f794eba74 263 pinFlag &= ~bWaveShape;
ryood 45:3c7143da38d1 264 SpiSendParams(CMD_WAVE_SHAPE, _waveShape);
ryood 28:d8614d2b82f9 265 isDirty = true;
ryood 18:309f794eba74 266 }
ryood 18:309f794eba74 267
ryood 28:d8614d2b82f9 268 if (pinFlag & bUIMode) {
ryood 18:309f794eba74 269 #if (UART_TRACE)
ryood 28:d8614d2b82f9 270 printf("PinUIMode Pushed\r\n");
ryood 18:309f794eba74 271 #endif
ryood 28:d8614d2b82f9 272 UImode++;
ryood 28:d8614d2b82f9 273 if (UImode > UImodeMax) {
ryood 28:d8614d2b82f9 274 UImode = 0;
ryood 18:309f794eba74 275 }
ryood 28:d8614d2b82f9 276 pinFlag &= ~bUIMode;
ryood 28:d8614d2b82f9 277 isDirty = true;
ryood 18:309f794eba74 278 }
ryood 18:309f794eba74 279
ryood 18:309f794eba74 280 if (pinFlag & bOctaveUp) {
ryood 18:309f794eba74 281 #if (UART_TRACE)
ryood 18:309f794eba74 282 printf("PinOctaveUp Pushed\r\n");
ryood 18:309f794eba74 283 #endif
ryood 43:12d11507c077 284 if (sequencerDisplay.getOctave() < octaveMax) {
ryood 40:2f9616bdcf65 285 sequencerDisplay.setOctave(sequencerDisplay.getOctave() + 1);
ryood 40:2f9616bdcf65 286 isDirty = true;
ryood 40:2f9616bdcf65 287 }
ryood 18:309f794eba74 288 pinFlag &= ~bOctaveUp;
ryood 18:309f794eba74 289 }
ryood 18:309f794eba74 290
ryood 18:309f794eba74 291 if (pinFlag & bOctaveDown) {
ryood 18:309f794eba74 292 #if (UART_TRACE)
ryood 18:309f794eba74 293 printf("PinOctaveDown Pushed\r\n");
ryood 18:309f794eba74 294 #endif
ryood 40:2f9616bdcf65 295 if (sequencerDisplay.getOctave () > octaveMin) {
ryood 40:2f9616bdcf65 296 sequencerDisplay.setOctave(sequencerDisplay.getOctave() - 1);
ryood 40:2f9616bdcf65 297 isDirty = true;
ryood 40:2f9616bdcf65 298 }
ryood 18:309f794eba74 299 pinFlag &= ~bOctaveDown;
ryood 18:309f794eba74 300 }
ryood 18:309f794eba74 301
ryood 18:309f794eba74 302 if (pinFlag & bNoteOnOff) {
ryood 18:309f794eba74 303 #if (UART_TRACE)
ryood 18:309f794eba74 304 printf("PinNoteOnOff Pushed\r\n");
ryood 18:309f794eba74 305 #endif
ryood 18:309f794eba74 306 sequences[currentStep].setNoteOn(!sequences[currentStep].isNoteOn());
ryood 18:309f794eba74 307 pinFlag &= ~bNoteOnOff;
ryood 45:3c7143da38d1 308 SpiSendParams(CMD_NOTE, getNoteData(currentStep));
ryood 28:d8614d2b82f9 309 isDirty = true;
ryood 18:309f794eba74 310 }
ryood 18:309f794eba74 311
ryood 18:309f794eba74 312 if (pinFlag & bTie) {
ryood 18:309f794eba74 313 #if (UART_TRACE)
ryood 18:309f794eba74 314 printf("PinTie Pushed\r\n");
ryood 18:309f794eba74 315 #endif
ryood 18:309f794eba74 316 sequences[currentStep].setTie(!sequences[currentStep].isTie());
ryood 18:309f794eba74 317 pinFlag &= ~bTie;
ryood 45:3c7143da38d1 318 SpiSendParams(CMD_NOTE, getNoteData(currentStep));
ryood 28:d8614d2b82f9 319 isDirty = true;
ryood 18:309f794eba74 320 }
ryood 18:309f794eba74 321
ryood 18:309f794eba74 322 if (pinFlag & bAccent) {
ryood 18:309f794eba74 323 #if (UART_TRACE)
ryood 18:309f794eba74 324 printf("PinAccent Pushed\r\n");
ryood 18:309f794eba74 325 #endif
ryood 18:309f794eba74 326 sequences[currentStep].setAccent(!sequences[currentStep].isAccent());
ryood 18:309f794eba74 327 pinFlag &= ~bAccent;
ryood 45:3c7143da38d1 328 SpiSendParams(CMD_NOTE, getNoteData(currentStep));
ryood 28:d8614d2b82f9 329 isDirty = true;
ryood 18:309f794eba74 330 }
ryood 18:309f794eba74 331
ryood 18:309f794eba74 332 if (pinFlag & bRunStop) {
ryood 18:309f794eba74 333 #if (UART_TRACE)
ryood 18:309f794eba74 334 printf("PinRunStop Pushed\r\n");
ryood 18:309f794eba74 335 #endif
ryood 18:309f794eba74 336 if (isRunning) {
ryood 18:309f794eba74 337 isRunning = false;
ryood 18:309f794eba74 338 } else {
ryood 18:309f794eba74 339 isRunning = true;
ryood 18:309f794eba74 340 }
ryood 18:309f794eba74 341 pinFlag &= ~bRunStop;
ryood 45:3c7143da38d1 342 SpiSendParams(CMD_RUN, isRunning);
ryood 28:d8614d2b82f9 343 isDirty = true;
ryood 18:309f794eba74 344 }
ryood 18:309f794eba74 345 }
ryood 18:309f794eba74 346
ryood 28:d8614d2b82f9 347 void dumpToLCD00()
ryood 16:b0419e3c9079 348 {
ryood 16:b0419e3c9079 349 char buff[64];
ryood 16:b0419e3c9079 350 int col = 0;
ryood 16:b0419e3c9079 351
ryood 16:b0419e3c9079 352 gLCD.clear();
ryood 16:b0419e3c9079 353
ryood 38:cafa2fff5565 354 sprintf(buff, "Run:%d BPM:%03d", isRunning, bpm);
ryood 16:b0419e3c9079 355 gLCD.drawstring(0, col++, buff);
ryood 24:040cdcb2ff14 356
ryood 24:040cdcb2ff14 357 sprintf(buff, "Stp:%02d Nto:%d Pch:%02d",
ryood 24:040cdcb2ff14 358 currentStep, sequences[currentStep].isNoteOn(), sequences[currentStep].getPitch());
ryood 24:040cdcb2ff14 359 gLCD.drawstring(0, col++, buff);
ryood 24:040cdcb2ff14 360
ryood 24:040cdcb2ff14 361 sprintf(buff, "Oct:%-2d Tie:%d Acc:%d",
ryood 26:fbf48a178aeb 362 sequencerDisplay.getOctave(), sequences[currentStep].isTie(),sequences[currentStep].isAccent());
ryood 16:b0419e3c9079 363 gLCD.drawstring(0, col++, buff);
ryood 16:b0419e3c9079 364
ryood 41:48864f5f5424 365 sprintf(buff, "Wsp:%d Mod:%d pStp:%d", oscillatorParam.waveShape, UImode, playingStep);
ryood 16:b0419e3c9079 366 gLCD.drawstring(0, col++, buff);
ryood 16:b0419e3c9079 367
ryood 38:cafa2fff5565 368 sprintf(buff, "PW :%4d CO :%4d", oscillatorParam.pulseWidth, filterParam.cutoff);
ryood 24:040cdcb2ff14 369 gLCD.drawstring(0, col++, buff);
ryood 38:cafa2fff5565 370 sprintf(buff, "RSO:%4d ACL:%4d", filterParam.resonance, accentLevel);
ryood 24:040cdcb2ff14 371 gLCD.drawstring(0, col++, buff);
ryood 38:cafa2fff5565 372 sprintf(buff, "LVL:%4d DUR:%4d", envelopeParam.level, envelopeParam.duration);
ryood 24:040cdcb2ff14 373 gLCD.drawstring(0, col++, buff);
ryood 38:cafa2fff5565 374 sprintf(buff, "DCY:%4d SUS:%4d", envelopeParam.decay, envelopeParam.sustain);
ryood 24:040cdcb2ff14 375 gLCD.drawstring(0, col++, buff);
ryood 16:b0419e3c9079 376
ryood 16:b0419e3c9079 377 gLCD.display();
ryood 16:b0419e3c9079 378 }
ryood 16:b0419e3c9079 379
ryood 28:d8614d2b82f9 380 void dumpToLCD01()
ryood 28:d8614d2b82f9 381 {
ryood 42:3c71f925a47b 382 static int errCutoff = 0;
ryood 42:3c71f925a47b 383 static int errDuration = 0;
ryood 42:3c71f925a47b 384 static int errDecay = 0;
ryood 42:3c71f925a47b 385 static int errSustain = 0;
ryood 42:3c71f925a47b 386 static int errResonace = 0;
ryood 42:3c71f925a47b 387 static int errLevel = 0;
ryood 42:3c71f925a47b 388 static int errPulseWidth = 0;
ryood 42:3c71f925a47b 389 static int errAccentLevel = 0;
ryood 42:3c71f925a47b 390
ryood 42:3c71f925a47b 391 uint8_t v;
ryood 28:d8614d2b82f9 392 char buff[64];
ryood 42:3c71f925a47b 393
ryood 42:3c71f925a47b 394 v = AinCutOff.read_u16() >> (16 - POT_RESOLUTION);
ryood 42:3c71f925a47b 395 if (v != filterParam.cutoff) {
ryood 42:3c71f925a47b 396 errCutoff++;
ryood 42:3c71f925a47b 397 filterParam.cutoff = v;
ryood 42:3c71f925a47b 398 }
ryood 42:3c71f925a47b 399 v = AinDuration.read_u16() >> (16 - POT_RESOLUTION);
ryood 42:3c71f925a47b 400 if (v != envelopeParam.duration) {
ryood 42:3c71f925a47b 401 errDuration++;
ryood 42:3c71f925a47b 402 envelopeParam.duration = v;
ryood 42:3c71f925a47b 403 }
ryood 42:3c71f925a47b 404 v = AinDecay.read_u16() >> (16 - POT_RESOLUTION);
ryood 42:3c71f925a47b 405 if (v != envelopeParam.decay) {
ryood 42:3c71f925a47b 406 errDecay++;
ryood 42:3c71f925a47b 407 envelopeParam.decay = v;
ryood 42:3c71f925a47b 408 }
ryood 42:3c71f925a47b 409 v = AinSustain.read_u16() >> (16 - POT_RESOLUTION);
ryood 42:3c71f925a47b 410 if (v != envelopeParam.sustain) {
ryood 42:3c71f925a47b 411 errSustain++;
ryood 42:3c71f925a47b 412 envelopeParam.sustain = v;
ryood 42:3c71f925a47b 413 }
ryood 42:3c71f925a47b 414
ryood 42:3c71f925a47b 415 v = AinResonance.read_u16() >> (16 - POT_RESOLUTION);
ryood 42:3c71f925a47b 416 if (v != filterParam.resonance) {
ryood 42:3c71f925a47b 417 errResonace++;
ryood 42:3c71f925a47b 418 filterParam.resonance = v;
ryood 42:3c71f925a47b 419 }
ryood 42:3c71f925a47b 420 v = AinLevel.read_u16() >> (16 - POT_RESOLUTION);
ryood 42:3c71f925a47b 421 if (v != envelopeParam.level) {
ryood 42:3c71f925a47b 422 errLevel++;
ryood 42:3c71f925a47b 423 envelopeParam.level = v;
ryood 42:3c71f925a47b 424 }
ryood 42:3c71f925a47b 425 v = AinPulseWidth.read_u16() >> (16 - POT_RESOLUTION);
ryood 42:3c71f925a47b 426 if (v != oscillatorParam.pulseWidth) {
ryood 42:3c71f925a47b 427 errPulseWidth++;
ryood 42:3c71f925a47b 428 oscillatorParam.pulseWidth = v;
ryood 42:3c71f925a47b 429 }
ryood 42:3c71f925a47b 430 v = AinAccentLevel.read_u16() >> (16 - POT_RESOLUTION);
ryood 42:3c71f925a47b 431 if (v != accentLevel) {
ryood 42:3c71f925a47b 432 errAccentLevel++;
ryood 42:3c71f925a47b 433 accentLevel = v;
ryood 42:3c71f925a47b 434 }
ryood 28:d8614d2b82f9 435
ryood 28:d8614d2b82f9 436 gLCD.clear();
ryood 28:d8614d2b82f9 437
ryood 42:3c71f925a47b 438 sprintf(buff, "Cutoff %3d %5d", filterParam.cutoff, errCutoff);
ryood 42:3c71f925a47b 439 gLCD.drawstring(0, 0, buff);
ryood 42:3c71f925a47b 440 sprintf(buff, "Duration %3d %5d", envelopeParam.duration, errDuration);
ryood 42:3c71f925a47b 441 gLCD.drawstring(0, 1, buff);
ryood 42:3c71f925a47b 442 sprintf(buff, "Decay %3d %5d", envelopeParam.decay, errDecay);
ryood 42:3c71f925a47b 443 gLCD.drawstring(0, 2, buff);
ryood 42:3c71f925a47b 444 sprintf(buff, "Sustain %3d %5d", envelopeParam.sustain, errSustain);
ryood 42:3c71f925a47b 445 gLCD.drawstring(0, 3, buff);
ryood 42:3c71f925a47b 446 sprintf(buff, "Resonance %3d %5d", filterParam.resonance, errResonace);
ryood 42:3c71f925a47b 447 gLCD.drawstring(0, 4, buff);
ryood 42:3c71f925a47b 448 sprintf(buff, "Level %3d %5d", envelopeParam.level, errLevel);
ryood 42:3c71f925a47b 449 gLCD.drawstring(0, 5, buff);
ryood 42:3c71f925a47b 450 sprintf(buff, "PulseWidth %3d %5d", oscillatorParam.pulseWidth, errPulseWidth);
ryood 42:3c71f925a47b 451 gLCD.drawstring(0, 6, buff);
ryood 42:3c71f925a47b 452 sprintf(buff, "AccentLvl %3d %5d", accentLevel, errAccentLevel);
ryood 42:3c71f925a47b 453 gLCD.drawstring(0, 7, buff);
ryood 28:d8614d2b82f9 454
ryood 28:d8614d2b82f9 455 gLCD.display();
ryood 42:3c71f925a47b 456 Thread::wait(10);
ryood 28:d8614d2b82f9 457 }
ryood 28:d8614d2b82f9 458
ryood 16:b0419e3c9079 459 //------------------------------------------------------------------------
ryood 47:f4c16d1e4207 460 // Threads
ryood 47:f4c16d1e4207 461 //------------------------------------------------------------------------
ryood 47:f4c16d1e4207 462
ryood 47:f4c16d1e4207 463 void pollingPots(void const *args)
ryood 47:f4c16d1e4207 464 {
ryood 47:f4c16d1e4207 465 for (;;)
ryood 47:f4c16d1e4207 466 {
ryood 47:f4c16d1e4207 467 uint8_t pulseWidth = AinPulseWidth.read_u16() >> (16 - POT_RESOLUTION);
ryood 47:f4c16d1e4207 468 if (pulseWidth != oscillatorParam.pulseWidth) {
ryood 47:f4c16d1e4207 469 oscillatorParam.pulseWidth = pulseWidth;
ryood 47:f4c16d1e4207 470 SpiSendParams(CMD_PULSE_WIDTH, pulseWidth);
ryood 47:f4c16d1e4207 471 isDirty = true;
ryood 47:f4c16d1e4207 472 }
ryood 47:f4c16d1e4207 473
ryood 47:f4c16d1e4207 474 uint8_t cutoff = AinCutOff.read_u16() >> (16 - POT_RESOLUTION);
ryood 47:f4c16d1e4207 475 if (cutoff != filterParam.cutoff) {
ryood 47:f4c16d1e4207 476 filterParam.cutoff = cutoff;
ryood 47:f4c16d1e4207 477 SpiSendParams(CMD_CUTOFF, cutoff);
ryood 47:f4c16d1e4207 478 isDirty = true;
ryood 47:f4c16d1e4207 479 }
ryood 47:f4c16d1e4207 480
ryood 47:f4c16d1e4207 481 uint8_t resonance = AinResonance.read_u16() >> (16 - POT_RESOLUTION);
ryood 47:f4c16d1e4207 482 if (resonance != filterParam.resonance) {
ryood 47:f4c16d1e4207 483 filterParam.resonance = resonance;
ryood 47:f4c16d1e4207 484 SpiSendParams(CMD_RESONANCE, resonance);
ryood 47:f4c16d1e4207 485 isDirty = true;
ryood 47:f4c16d1e4207 486 }
ryood 47:f4c16d1e4207 487
ryood 47:f4c16d1e4207 488 uint8_t level = AinLevel.read_u16() >> (16 - POT_RESOLUTION);
ryood 47:f4c16d1e4207 489 if (level != envelopeParam.level) {
ryood 47:f4c16d1e4207 490 envelopeParam.level = level;
ryood 47:f4c16d1e4207 491 SpiSendParams(CMD_LEVEL, level);
ryood 47:f4c16d1e4207 492 isDirty = true;
ryood 47:f4c16d1e4207 493 }
ryood 47:f4c16d1e4207 494
ryood 47:f4c16d1e4207 495 uint8_t duration = AinDuration.read_u16() >> (16 - POT_RESOLUTION);
ryood 47:f4c16d1e4207 496 if (duration != envelopeParam.duration) {
ryood 47:f4c16d1e4207 497 envelopeParam.duration = duration;
ryood 47:f4c16d1e4207 498 SpiSendParams(CMD_DURATION, duration);
ryood 47:f4c16d1e4207 499 isDirty = true;
ryood 47:f4c16d1e4207 500 }
ryood 47:f4c16d1e4207 501
ryood 47:f4c16d1e4207 502 uint8_t decay = AinDecay.read_u16() >> (16 - POT_RESOLUTION);
ryood 47:f4c16d1e4207 503 if (decay != envelopeParam.decay) {
ryood 47:f4c16d1e4207 504 envelopeParam.decay = decay;
ryood 47:f4c16d1e4207 505 SpiSendParams(CMD_DECAY, decay);
ryood 47:f4c16d1e4207 506 isDirty = true;
ryood 47:f4c16d1e4207 507 }
ryood 47:f4c16d1e4207 508
ryood 47:f4c16d1e4207 509 uint8_t sustain = AinSustain.read_u16() >> (16 - POT_RESOLUTION);
ryood 47:f4c16d1e4207 510 if (sustain != envelopeParam.sustain) {
ryood 47:f4c16d1e4207 511 envelopeParam.sustain = sustain;
ryood 47:f4c16d1e4207 512 SpiSendParams(CMD_SUSTAIN, sustain);
ryood 47:f4c16d1e4207 513 isDirty = true;
ryood 47:f4c16d1e4207 514 }
ryood 47:f4c16d1e4207 515
ryood 47:f4c16d1e4207 516 uint8_t _accentLevel = AinAccentLevel.read_u16() >> (16 - POT_RESOLUTION);
ryood 47:f4c16d1e4207 517 if (_accentLevel != accentLevel) {
ryood 47:f4c16d1e4207 518 accentLevel = _accentLevel;
ryood 47:f4c16d1e4207 519 SpiSendParams(CMD_ACCENT_LEVEL, accentLevel);
ryood 47:f4c16d1e4207 520 isDirty = true;
ryood 47:f4c16d1e4207 521 }
ryood 47:f4c16d1e4207 522
ryood 47:f4c16d1e4207 523 Thread::wait(POLLING_POTS_WAIT);
ryood 47:f4c16d1e4207 524 }
ryood 47:f4c16d1e4207 525 }
ryood 47:f4c16d1e4207 526
ryood 47:f4c16d1e4207 527 //------------------------------------------------------------------------
ryood 16:b0419e3c9079 528 // Main routine
ryood 16:b0419e3c9079 529 //------------------------------------------------------------------------
ryood 0:21e39bc75e31 530 int main()
ryood 0:21e39bc75e31 531 {
ryood 18:309f794eba74 532 #if (UART_TRACE)
ryood 38:cafa2fff5565 533 printf("*** BaseMachine UI Controller ***\r\n");
ryood 18:309f794eba74 534 #endif
ryood 18:309f794eba74 535
ryood 24:040cdcb2ff14 536 //--------------------------------------------------------------------
ryood 16:b0419e3c9079 537 // Setup Devices
ryood 16:b0419e3c9079 538 //
ryood 38:cafa2fff5565 539 gLCD.set_spi_frequency(SPI2_RATE);
ryood 16:b0419e3c9079 540 gLCD.begin(0x12);
ryood 16:b0419e3c9079 541 gLCD.clear();
ryood 16:b0419e3c9079 542 gLCD.drawstring(0, 0, TITLE_STR1);
ryood 16:b0419e3c9079 543 gLCD.drawstring(0, 1, TITLE_STR2);
ryood 16:b0419e3c9079 544 gLCD.display();
ryood 16:b0419e3c9079 545 Thread::wait(1000);
ryood 16:b0419e3c9079 546
ryood 20:00d3b6ace8c7 547 RotEncStep.setInterval(100);
ryood 20:00d3b6ace8c7 548 RotEncPitch.setInterval(100);
ryood 20:00d3b6ace8c7 549 RotEncBpm.setInterval(100);
ryood 17:557658db3e81 550
ryood 18:309f794eba74 551 PinWaveShape.attach_asserted(&swWaveShapePressed);
ryood 18:309f794eba74 552 PinWaveShape.setAssertValue(0);
ryood 18:309f794eba74 553 PinWaveShape.setSampleFrequency();
ryood 18:309f794eba74 554
ryood 28:d8614d2b82f9 555 PinUIMode.attach_asserted(&swUIModePressed);
ryood 28:d8614d2b82f9 556 PinUIMode.setAssertValue(0);
ryood 28:d8614d2b82f9 557 PinUIMode.setSampleFrequency();
ryood 18:309f794eba74 558
ryood 18:309f794eba74 559 PinOctaveUp.attach_asserted(&swOctaveUpPressed);
ryood 18:309f794eba74 560 PinOctaveUp.setAssertValue(0);
ryood 18:309f794eba74 561 PinOctaveUp.setSampleFrequency();
ryood 18:309f794eba74 562
ryood 18:309f794eba74 563 PinOctaveDown.attach_asserted(&swOctaveDownPressed);
ryood 18:309f794eba74 564 PinOctaveDown.setAssertValue(0);
ryood 18:309f794eba74 565 PinOctaveDown.setSampleFrequency();
ryood 18:309f794eba74 566
ryood 18:309f794eba74 567 PinNoteOnOff.attach_asserted(&swNoteOnOffPressed);
ryood 18:309f794eba74 568 PinNoteOnOff.setAssertValue(0);
ryood 18:309f794eba74 569 PinNoteOnOff.setSampleFrequency();
ryood 18:309f794eba74 570
ryood 18:309f794eba74 571 PinTie.attach_asserted(&swTiePressed);
ryood 18:309f794eba74 572 PinTie.setAssertValue(0);
ryood 18:309f794eba74 573 PinTie.setSampleFrequency();
ryood 18:309f794eba74 574
ryood 18:309f794eba74 575 PinAccent.attach_asserted(&swAccentPressed);
ryood 18:309f794eba74 576 PinAccent.setAssertValue(0);
ryood 18:309f794eba74 577 PinAccent.setSampleFrequency();
ryood 18:309f794eba74 578
ryood 18:309f794eba74 579 PinRunStop.attach_asserted(&swRunStopPressed);
ryood 18:309f794eba74 580 PinRunStop.setAssertValue(0);
ryood 41:48864f5f5424 581 PinRunStop.setSampleFrequency();
ryood 41:48864f5f5424 582
ryood 41:48864f5f5424 583 //--------------------------------------------------------------------
ryood 41:48864f5f5424 584 // Initialize SPI Master
ryood 41:48864f5f5424 585 //
ryood 41:48864f5f5424 586 SpiMasterCs = 1;
ryood 44:b1bdccdbf67e 587 SpiMaster.format(16, 0);
ryood 53:cad31fd61d8a 588 SpiMaster.frequency(SPI_UI_TO_SEQUENCER_RATE);
ryood 41:48864f5f5424 589
ryood 53:cad31fd61d8a 590 StepChangeInterrupt.fall(&updateStep);
ryood 18:309f794eba74 591
ryood 24:040cdcb2ff14 592 //--------------------------------------------------------------------
ryood 22:82f1e7877f9f 593 // Initialize objects
ryood 0:21e39bc75e31 594 //
ryood 15:9813d8eaf57e 595 Sequence::setBaseNoteNumber(baseNoteNumber);
ryood 14:c173e03ee3ad 596
ryood 0:21e39bc75e31 597 for (int i = 0; i < SEQUENCE_N; i++) {
ryood 38:cafa2fff5565 598 Sequence& seq = sequences[i];
ryood 14:c173e03ee3ad 599 seq.setPitch(pitch[i]);
ryood 15:9813d8eaf57e 600 seq.setNoteOn(noteOn[i]);
ryood 15:9813d8eaf57e 601 seq.setTie(tie[i]);
ryood 26:fbf48a178aeb 602 seq.setAccent(accent[i]);
ryood 0:21e39bc75e31 603 }
ryood 26:fbf48a178aeb 604 RotEncPitch.setVal(sequences[0].getPitch());
ryood 6:fc10eac60b91 605
ryood 24:040cdcb2ff14 606 //--------------------------------------------------------------------
ryood 47:f4c16d1e4207 607 // Initialize threads
ryood 47:f4c16d1e4207 608 //
ryood 47:f4c16d1e4207 609 Thread thPollingPots(pollingPots);
ryood 49:22e651444533 610
ryood 49:22e651444533 611 //--------------------------------------------------------------------
ryood 49:22e651444533 612 // Synchronize with Slave
ryood 49:22e651444533 613 //
ryood 54:38187ac44253 614 SlaveReset = 0;
ryood 54:38187ac44253 615 SlaveReset = 1;
ryood 54:38187ac44253 616 Thread::wait(1000);
ryood 49:22e651444533 617 SpiSendAllParams();
ryood 47:f4c16d1e4207 618
ryood 47:f4c16d1e4207 619 //--------------------------------------------------------------------
ryood 24:040cdcb2ff14 620 // Main loop
ryood 24:040cdcb2ff14 621 //
ryood 5:4abac408b827 622 for (;;) {
ryood 41:48864f5f5424 623 // Polling Devices
ryood 47:f4c16d1e4207 624 /*
ryood 42:3c71f925a47b 625 if (UImode != 2) {
ryood 42:3c71f925a47b 626 pollingPots();
ryood 42:3c71f925a47b 627 }
ryood 47:f4c16d1e4207 628 */
ryood 20:00d3b6ace8c7 629 pollingRotEncs();
ryood 18:309f794eba74 630 pollingPins();
ryood 41:48864f5f5424 631
ryood 44:b1bdccdbf67e 632 // Recieve playing step from SPI slave
ryood 44:b1bdccdbf67e 633 if (isStepChanged) {
ryood 44:b1bdccdbf67e 634 uint16_t recievedVal = SpiSendParams(CMD_RCV_PLAYING_STEP, 0x55); // Send dummy data
ryood 44:b1bdccdbf67e 635 playingStep = (uint8_t)(recievedVal & 0xff);
ryood 44:b1bdccdbf67e 636 isStepChanged = false;
ryood 44:b1bdccdbf67e 637 isDirty = true;
ryood 44:b1bdccdbf67e 638 }
ryood 41:48864f5f5424 639
ryood 41:48864f5f5424 640 // Display
ryood 50:0a06df15c784 641 /*
ryood 23:5fe70293e34c 642 if (!isRunning) {
ryood 50:0a06df15c784 643 */
ryood 25:7382bc0a0329 644 if (isDirty) {
ryood 28:d8614d2b82f9 645 switch (UImode) {
ryood 28:d8614d2b82f9 646 case 0:
ryood 37:d4e50159baee 647 sequencerDisplay.update(SequencerDisplay::stop, currentStep, playingStep);
ryood 28:d8614d2b82f9 648 break;
ryood 28:d8614d2b82f9 649 case 1:
ryood 28:d8614d2b82f9 650 dumpToLCD00();
ryood 28:d8614d2b82f9 651 break;
ryood 28:d8614d2b82f9 652 }
ryood 28:d8614d2b82f9 653 isDirty = false;
ryood 28:d8614d2b82f9 654 }
ryood 28:d8614d2b82f9 655 if (UImode == 2) {
ryood 28:d8614d2b82f9 656 dumpToLCD01();
ryood 28:d8614d2b82f9 657 }
ryood 50:0a06df15c784 658 /*
ryood 28:d8614d2b82f9 659 } else {
ryood 50:0a06df15c784 660 */
ryood 28:d8614d2b82f9 661 if (isDirty) {
ryood 37:d4e50159baee 662 sequencerDisplay.update(SequencerDisplay::run, currentStep, playingStep);
ryood 36:50ad7e0a9a95 663 isDirty = false;
ryood 25:7382bc0a0329 664 }
ryood 50:0a06df15c784 665 /*
ryood 23:5fe70293e34c 666 }
ryood 50:0a06df15c784 667 */
ryood 5:4abac408b827 668 }
ryood 0:21e39bc75e31 669 }