BaseMachine UI Controllerに分離

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

Fork of BaseMachine_Sequencer by Ryo Od

Committer:
ryood
Date:
Fri Oct 07 10:41:48 2016 +0000
Revision:
46:0fb579ecdd77
Parent:
45:3c7143da38d1
Child:
47:f4c16d1e4207
Impl. Rotary Encoder

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