PokittoLib is the library needed for programming the Pokitto DIY game console (www.pokitto.com)

Committer:
spinal
Date:
Sun Nov 18 15:47:54 2018 +0000
Revision:
64:6e6c6c2b664e
Parent:
58:5f58a2846a20
added fix for directrectangle()

Who changed what in which revision?

UserRevisionLine numberNew contents of line
Pokitto 52:c04087025cab 1 /**************************************************************************/
Pokitto 52:c04087025cab 2 /*!
Pokitto 52:c04087025cab 3 @file PokittoSound.cpp
Pokitto 52:c04087025cab 4 @author Jonne Valola
Pokitto 52:c04087025cab 5
Pokitto 52:c04087025cab 6 @section LICENSE
Pokitto 52:c04087025cab 7
Pokitto 52:c04087025cab 8 Software License Agreement (BSD License)
Pokitto 52:c04087025cab 9
Pokitto 52:c04087025cab 10 Copyright (c) 2016, Jonne Valola
Pokitto 52:c04087025cab 11 All rights reserved.
Pokitto 52:c04087025cab 12
Pokitto 52:c04087025cab 13 Redistribution and use in source and binary forms, with or without
Pokitto 52:c04087025cab 14 modification, are permitted provided that the following conditions are met:
Pokitto 52:c04087025cab 15 1. Redistributions of source code must retain the above copyright
Pokitto 52:c04087025cab 16 notice, this list of conditions and the following disclaimer.
Pokitto 52:c04087025cab 17 2. Redistributions in binary form must reproduce the above copyright
Pokitto 52:c04087025cab 18 notice, this list of conditions and the following disclaimer in the
Pokitto 52:c04087025cab 19 documentation and/or other materials provided with the distribution.
Pokitto 52:c04087025cab 20 3. Neither the name of the copyright holders nor the
Pokitto 52:c04087025cab 21 names of its contributors may be used to endorse or promote products
Pokitto 52:c04087025cab 22 derived from this software without specific prior written permission.
Pokitto 52:c04087025cab 23
Pokitto 52:c04087025cab 24 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ''AS IS'' AND ANY
Pokitto 52:c04087025cab 25 EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
Pokitto 52:c04087025cab 26 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
Pokitto 52:c04087025cab 27 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
Pokitto 52:c04087025cab 28 DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
Pokitto 52:c04087025cab 29 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
Pokitto 52:c04087025cab 30 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
Pokitto 52:c04087025cab 31 ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
Pokitto 52:c04087025cab 32 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
Pokitto 52:c04087025cab 33 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
Pokitto 52:c04087025cab 34 */
Pokitto 52:c04087025cab 35 /**************************************************************************/
Pokitto 52:c04087025cab 36
Pokitto 52:c04087025cab 37 /*
Pokitto 52:c04087025cab 38 * NOTE:
Pokitto 52:c04087025cab 39 * API of the Pokitto Sound library is partially identical to the Gamebuino Sound API.
Pokitto 52:c04087025cab 40 * Due to the difference in architecture (ARM Cortex-M0+ in mbed environment vs. 8-bit AVR)
Pokitto 52:c04087025cab 41 * large parts are not identical. Most functions were rewritten, with only API remaining.
Pokitto 52:c04087025cab 42 * We want to give attribution to the original author's project:
Pokitto 52:c04087025cab 43 *
Pokitto 52:c04087025cab 44 * License for Gamebuino-identical code:
Pokitto 52:c04087025cab 45 *
Pokitto 58:5f58a2846a20 46 * (C) Copyright 2014 Aur�lien Rodot. All rights reserved.
Pokitto 52:c04087025cab 47 *
Pokitto 52:c04087025cab 48 * This file is part of the Gamebuino Library (http://gamebuino.com)
Pokitto 52:c04087025cab 49 *
Pokitto 52:c04087025cab 50 * The Gamebuino Library is free software: you can redistribute it and/or modify
Pokitto 52:c04087025cab 51 * it under the terms of the GNU Lesser General Public License as published by
Pokitto 52:c04087025cab 52 * the Free Software Foundation, either version 3 of the License, or
Pokitto 52:c04087025cab 53 * (at your option) any later version.
Pokitto 52:c04087025cab 54 *
Pokitto 52:c04087025cab 55 * This program is distributed in the hope that it will be useful,
Pokitto 52:c04087025cab 56 * but WITHOUT ANY WARRANTY; without even the implied warranty of
Pokitto 52:c04087025cab 57 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
Pokitto 52:c04087025cab 58 * GNU Lesser General Public License for more details.
Pokitto 52:c04087025cab 59 *
Pokitto 52:c04087025cab 60 * You should have received a copy of the GNU Lesser General Public License
Pokitto 52:c04087025cab 61 * along with this program. If not, see <http://www.gnu.org/licenses/>
Pokitto 52:c04087025cab 62 */
Pokitto 52:c04087025cab 63
Pokitto 52:c04087025cab 64 #include "PokittoSound.h"
Pokitto 52:c04087025cab 65 #include "Pokitto_settings.h"
Pokitto 52:c04087025cab 66 #include "PokittoCore.h"
Pokitto 52:c04087025cab 67 #include "Synth.h"
Pokitto 52:c04087025cab 68
Pokitto 52:c04087025cab 69 #ifndef POK_SIM
Pokitto 52:c04087025cab 70 #include "HWSound.h"
Pokitto 52:c04087025cab 71 #else
Pokitto 52:c04087025cab 72 #include "SimSound.h"
Pokitto 52:c04087025cab 73 #include "PokittoSimulator.h"
Pokitto 52:c04087025cab 74 #endif
Pokitto 52:c04087025cab 75
Pokitto 52:c04087025cab 76 typedef uint8_t byte;
Pokitto 52:c04087025cab 77
Pokitto 52:c04087025cab 78 using namespace Pokitto;
Pokitto 52:c04087025cab 79
Pokitto 52:c04087025cab 80 /** discrete hardware volume control **/
Pokitto 52:c04087025cab 81
Pokitto 52:c04087025cab 82 uint8_t Pokitto::discrete_vol = 0;
Pokitto 58:5f58a2846a20 83 uint8_t const Pokitto::discrete_vol_levels[] = {0,32,64,96,128,160,192,224};
Pokitto 58:5f58a2846a20 84 uint8_t const Pokitto::discrete_vol_hw_levels[] = {0,27,64,96,36,117,127,127};
Pokitto 58:5f58a2846a20 85 uint8_t const Pokitto::discrete_vol_multipliers[] = {0,127,127,127,192,192,255,255};
Pokitto 52:c04087025cab 86
Pokitto 52:c04087025cab 87 Pokitto::Core _soundc;
Pokitto 52:c04087025cab 88
Pokitto 52:c04087025cab 89 uint8_t Sound::prescaler;
Pokitto 52:c04087025cab 90 uint16_t Sound::globalVolume;
Pokitto 52:c04087025cab 91 uint16_t Sound::volumeMax = VOLUME_HEADPHONE_MAX;
Pokitto 52:c04087025cab 92 uint8_t Sound::headPhoneLevel=1;
Pokitto 52:c04087025cab 93
Pokitto 52:c04087025cab 94 bool Sound::trackIsPlaying[NUM_CHANNELS];
Pokitto 52:c04087025cab 95 bool Sound::patternIsPlaying[NUM_CHANNELS];
Pokitto 52:c04087025cab 96 uint8_t Sound::outputPitch[NUM_CHANNELS];
Pokitto 52:c04087025cab 97 int8_t Sound::outputVolume[NUM_CHANNELS];
Pokitto 52:c04087025cab 98
Pokitto 52:c04087025cab 99 uint16_t *Sound::trackData[NUM_CHANNELS];
Pokitto 52:c04087025cab 100 uint8_t Sound::trackCursor[NUM_CHANNELS];
Pokitto 52:c04087025cab 101 uint16_t **Sound::patternSet[NUM_CHANNELS];
Pokitto 52:c04087025cab 102 int8_t Sound::patternPitch[NUM_CHANNELS];
Pokitto 52:c04087025cab 103
Pokitto 52:c04087025cab 104 // pattern data
Pokitto 52:c04087025cab 105 uint16_t *Sound::patternData[NUM_CHANNELS];
Pokitto 52:c04087025cab 106 uint16_t **Sound::instrumentSet[NUM_CHANNELS];
Pokitto 52:c04087025cab 107 bool Sound::patternLooping[NUM_CHANNELS];
Pokitto 52:c04087025cab 108 uint16_t Sound::patternCursor[NUM_CHANNELS];
Pokitto 52:c04087025cab 109
Pokitto 52:c04087025cab 110 // note data
Pokitto 52:c04087025cab 111 uint8_t Sound::notePitch[NUM_CHANNELS];
Pokitto 52:c04087025cab 112 uint8_t Sound::noteDuration[NUM_CHANNELS];
Pokitto 52:c04087025cab 113 int8_t Sound::noteVolume[NUM_CHANNELS];
Pokitto 52:c04087025cab 114 bool Sound::notePlaying[NUM_CHANNELS];
Pokitto 52:c04087025cab 115
Pokitto 52:c04087025cab 116 // commands data
Pokitto 52:c04087025cab 117 int8_t Sound::commandsCounter[NUM_CHANNELS];
Pokitto 52:c04087025cab 118 int8_t Sound::volumeSlideStepDuration[NUM_CHANNELS];
Pokitto 52:c04087025cab 119 int8_t Sound::volumeSlideStepSize[NUM_CHANNELS];
Pokitto 52:c04087025cab 120 uint8_t Sound::arpeggioStepDuration[NUM_CHANNELS];
Pokitto 52:c04087025cab 121 int8_t Sound::arpeggioStepSize[NUM_CHANNELS];
Pokitto 52:c04087025cab 122 uint8_t Sound::tremoloStepDuration[NUM_CHANNELS];
Pokitto 52:c04087025cab 123 int8_t Sound::tremoloStepSize[NUM_CHANNELS];
Pokitto 52:c04087025cab 124
Pokitto 52:c04087025cab 125 // instrument data
Pokitto 52:c04087025cab 126 uint16_t *Sound::instrumentData[NUM_CHANNELS];
Pokitto 52:c04087025cab 127 uint8_t Sound::instrumentLength[NUM_CHANNELS]; //number of steps in the instrument
Pokitto 52:c04087025cab 128 uint8_t Sound::instrumentLooping[NUM_CHANNELS]; //how many steps to loop on when the last step of the instrument is reached
Pokitto 52:c04087025cab 129 uint16_t Sound::instrumentCursor[NUM_CHANNELS]; //which step is being played
Pokitto 52:c04087025cab 130 uint8_t Sound::instrumentNextChange[NUM_CHANNELS]; //how many frames before the next step
Pokitto 52:c04087025cab 131
Pokitto 52:c04087025cab 132 //current step data
Pokitto 52:c04087025cab 133 int8_t Sound::stepVolume[NUM_CHANNELS];
Pokitto 52:c04087025cab 134 uint8_t Sound::stepPitch[NUM_CHANNELS];
Pokitto 52:c04087025cab 135 uint8_t Sound::chanVolumes[NUM_CHANNELS];
Pokitto 52:c04087025cab 136
Pokitto 52:c04087025cab 137 #if (POK_ENABLE_SOUND < 1)
Pokitto 58:5f58a2846a20 138 #undef NUM_CHANNELS
Pokitto 52:c04087025cab 139 #define NUM_CHANNELS 0
Pokitto 52:c04087025cab 140 #endif
Pokitto 52:c04087025cab 141
Pokitto 52:c04087025cab 142 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 143 #ifndef POK_SIM
Pokitto 52:c04087025cab 144 uint32_t sbyte;
Pokitto 52:c04087025cab 145 #else
Pokitto 52:c04087025cab 146 uint32_t sbyte;
Pokitto 52:c04087025cab 147 float pwm1;
Pokitto 52:c04087025cab 148 #endif // POK_SIM
Pokitto 52:c04087025cab 149
Pokitto 52:c04087025cab 150 //declare these variables globally for faster access
Pokitto 52:c04087025cab 151 uint8_t _rand = 1;
Pokitto 52:c04087025cab 152 uint8_t _chanCount[NUM_CHANNELS]; //counts until the next change of the waveform
Pokitto 52:c04087025cab 153 bool _chanState[NUM_CHANNELS]; //if the waveform is currently high or low
Pokitto 52:c04087025cab 154 uint8_t _chanHalfPeriod[NUM_CHANNELS]; //duration of half the period of the waveform
Pokitto 52:c04087025cab 155 uint8_t _chanOutputVolume[NUM_CHANNELS]; //amplitude of the outputted waveform
Pokitto 52:c04087025cab 156 uint8_t _chanOutput[NUM_CHANNELS]; //current value of the outputted waveform
Pokitto 52:c04087025cab 157 bool _chanNoise[NUM_CHANNELS]; //if a random value should be added to the waveform to generate noise
Pokitto 52:c04087025cab 158
Pokitto 52:c04087025cab 159 #if POK_GBSOUND > 0
Pokitto 52:c04087025cab 160 const uint16_t squareWaveInstrument[] = {0x0101, 0x03F7};
Pokitto 52:c04087025cab 161 const uint16_t noiseInstrument[] = {0x0101, 0x03FF};
Pokitto 52:c04087025cab 162 const uint16_t* const defaultInstruments[] = {squareWaveInstrument,noiseInstrument};
Pokitto 52:c04087025cab 163
Pokitto 52:c04087025cab 164 const uint16_t playOKPattern[] = {0x0005,0x138,0x168,0x0000};
Pokitto 52:c04087025cab 165 const uint16_t playCancelPattern[] = {0x0005,0x168,0x138,0x0000};
Pokitto 52:c04087025cab 166 const uint16_t playTickP[] = {0x0045,0x168,0x0000};
Pokitto 52:c04087025cab 167 #endif
Pokitto 52:c04087025cab 168 #if(EXTENDED_NOTE_RANGE > 0)
Pokitto 52:c04087025cab 169 //extended note range
Pokitto 52:c04087025cab 170 #define NUM_PITCH 59
Pokitto 52:c04087025cab 171 const uint8_t _halfPeriods[NUM_PITCH] = {246,232,219,207,195,184,174,164,155,146,138,130,123,116,110,104,98,92,87,82,78,73,69,65,62,58,55,52,49,46,44,41,39,37,35,33,31,29,28,26,25,23,22,21,20,19,18,17,16,15,14,13,12,11,10,9,8,7,6};
Pokitto 52:c04087025cab 172 #else
Pokitto 52:c04087025cab 173 //regular note range
Pokitto 52:c04087025cab 174 #define NUM_PITCH 36
Pokitto 52:c04087025cab 175 const uint8_t _halfPeriods[NUM_PITCH] = {246,232,219,207,195,184,174,164,155,146,138,130,123,116,110,104,98,92,87,82,78,73,69,65,62,58,55,52,49,46,44,41,39,37,35,33};
Pokitto 52:c04087025cab 176 #endif
Pokitto 52:c04087025cab 177
Pokitto 52:c04087025cab 178 #endif
Pokitto 52:c04087025cab 179
Pokitto 52:c04087025cab 180 void Pokitto::audio_IRQ() {
Pokitto 52:c04087025cab 181 #if POK_STREAMING_MUSIC > 0
Pokitto 52:c04087025cab 182 #if POK_STREAMFREQ_HALVE > 0
Pokitto 52:c04087025cab 183 streamstep = 1-streamstep;
Pokitto 52:c04087025cab 184 #else
Pokitto 52:c04087025cab 185 streamstep=1;
Pokitto 52:c04087025cab 186 #endif
Pokitto 52:c04087025cab 187
Pokitto 52:c04087025cab 188 streamstep &= streamon; //check if stream is on
Pokitto 52:c04087025cab 189
Pokitto 52:c04087025cab 190 if(streamvol && streamstep) {
Pokitto 52:c04087025cab 191 uint8_t output = (*currentPtr++);
Pokitto 52:c04087025cab 192 sbyte = output;
Pokitto 52:c04087025cab 193 } else {
Pokitto 52:c04087025cab 194 sbyte = 0; // duty cycle
Pokitto 52:c04087025cab 195 }
Pokitto 52:c04087025cab 196
Pokitto 52:c04087025cab 197 if (currentPtr >= endPtr)
Pokitto 52:c04087025cab 198 {
Pokitto 52:c04087025cab 199 currentBuffer++;
Pokitto 52:c04087025cab 200 if (currentBuffer==4) currentBuffer=0;
Pokitto 52:c04087025cab 201 currentPtr = buffers[currentBuffer];
Pokitto 52:c04087025cab 202 endPtr = currentPtr + BUFFER_SIZE;
Pokitto 52:c04087025cab 203 }
Pokitto 52:c04087025cab 204
Pokitto 52:c04087025cab 205 #endif // POK_STREAMING_MUSIC
Pokitto 52:c04087025cab 206 #if (NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 207 Sound::generateOutput();
Pokitto 52:c04087025cab 208 #endif
Pokitto 52:c04087025cab 209 }
Pokitto 52:c04087025cab 210
Pokitto 52:c04087025cab 211 void Sound::volumeUp() {
Pokitto 52:c04087025cab 212 Pokitto::discrete_vol++;
Pokitto 52:c04087025cab 213 if (discrete_vol>7) discrete_vol=7;
Pokitto 52:c04087025cab 214 globalVolume = discrete_vol_levels[discrete_vol];
Pokitto 52:c04087025cab 215 setVolume(globalVolume);
Pokitto 52:c04087025cab 216 //if (globalVolume>VOLUME_HEADPHONE_MAX) setVolume(getVolume()+VOLUME_STEP*2);
Pokitto 52:c04087025cab 217 //else setVolume(getVolume()+VOLUME_STEP);
Pokitto 52:c04087025cab 218 }
Pokitto 52:c04087025cab 219
Pokitto 52:c04087025cab 220 void Sound::volumeDown() {
Pokitto 52:c04087025cab 221 if (discrete_vol) Pokitto::discrete_vol--;
Pokitto 52:c04087025cab 222 globalVolume = discrete_vol_levels[discrete_vol];
Pokitto 52:c04087025cab 223 setVolume(globalVolume);
Pokitto 52:c04087025cab 224 //if (globalVolume>VOLUME_HEADPHONE_MAX) setVolume(getVolume()-VOLUME_STEP*4);
Pokitto 52:c04087025cab 225 //else setVolume(getVolume()-VOLUME_STEP);
Pokitto 52:c04087025cab 226 }
Pokitto 52:c04087025cab 227
Pokitto 52:c04087025cab 228
Pokitto 52:c04087025cab 229 void Sound::setMaxVol(int16_t v) {
Pokitto 52:c04087025cab 230 if (v < 0) v = 0; //prevent nasty wraparound
Pokitto 52:c04087025cab 231 if (v > VOLUME_SPEAKER_MAX) {
Pokitto 52:c04087025cab 232 v = VOLUME_SPEAKER_MAX;
Pokitto 52:c04087025cab 233 }
Pokitto 52:c04087025cab 234 volumeMax = v;
Pokitto 52:c04087025cab 235 setVolume(globalVolume);
Pokitto 52:c04087025cab 236 }
Pokitto 52:c04087025cab 237
Pokitto 52:c04087025cab 238 uint16_t Sound::getMaxVol() {
Pokitto 52:c04087025cab 239 return volumeMax;
Pokitto 52:c04087025cab 240 }
Pokitto 52:c04087025cab 241
Pokitto 52:c04087025cab 242 void Sound::updateStream() {
Pokitto 52:c04087025cab 243 #if POK_STREAMING_MUSIC
Pokitto 52:c04087025cab 244 if (oldBuffer != currentBuffer) {
Pokitto 52:c04087025cab 245 if (currentBuffer==0) fileReadBytes(&buffers[3][0],BUFFER_SIZE);
Pokitto 52:c04087025cab 246 else if (currentBuffer==1) fileReadBytes(&buffers[0][0],BUFFER_SIZE);
Pokitto 52:c04087025cab 247 else if (currentBuffer==2) fileReadBytes(&buffers[1][0],BUFFER_SIZE);
Pokitto 52:c04087025cab 248 else fileReadBytes(&buffers[2][0],BUFFER_SIZE);
Pokitto 52:c04087025cab 249 oldBuffer = currentBuffer;
Pokitto 52:c04087025cab 250 streamcounter += BUFFER_SIZE;
Pokitto 52:c04087025cab 251 }
Pokitto 52:c04087025cab 252
Pokitto 52:c04087025cab 253 #ifndef POK_SIM
Pokitto 52:c04087025cab 254 if ( streamcounter > fs.fsize - (BUFFER_SIZE)) {
Pokitto 52:c04087025cab 255 #else
Pokitto 52:c04087025cab 256 if ( streamcounter > getFileLength() - (BUFFER_SIZE)) {
Pokitto 52:c04087025cab 257 #endif
Pokitto 52:c04087025cab 258 streamcounter=0;
Pokitto 52:c04087025cab 259 #if POK_STREAM_LOOP > 0
Pokitto 52:c04087025cab 260 fileRewind();
Pokitto 52:c04087025cab 261 #else
Pokitto 52:c04087025cab 262 #ifndef POK_SIM
Pokitto 52:c04087025cab 263 streamon=0;
Pokitto 52:c04087025cab 264 #endif // POK_SIM
Pokitto 52:c04087025cab 265 #endif // POK_STREAM_LOOP
Pokitto 52:c04087025cab 266 }
Pokitto 52:c04087025cab 267 #endif
Pokitto 52:c04087025cab 268 }
Pokitto 52:c04087025cab 269
Pokitto 52:c04087025cab 270 void Sound::begin() {
Pokitto 52:c04087025cab 271 #if POK_ENABLE_SOUND > 0
Pokitto 52:c04087025cab 272 soundInit();
Pokitto 52:c04087025cab 273 ampEnable(true);
Pokitto 52:c04087025cab 274 #endif
Pokitto 52:c04087025cab 275 #if (NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 276 #if POK_ENABLE_SOUND > 0
Pokitto 52:c04087025cab 277 #if POK_GBSOUND > 0
Pokitto 52:c04087025cab 278 prescaler = 1;
Pokitto 52:c04087025cab 279 for(byte i=0; i<NUM_CHANNELS; i++){
Pokitto 52:c04087025cab 280 chanVolumes[i] = VOLUME_CHANNEL_MAX;
Pokitto 52:c04087025cab 281 changeInstrumentSet(defaultInstruments, i); //load default instruments. #0:square wave, #1: noise
Pokitto 52:c04087025cab 282 command(CMD_INSTRUMENT, 0, 0, i); //set the default instrument to square wave
Pokitto 52:c04087025cab 283 }
Pokitto 52:c04087025cab 284 #endif // POK_GBSOUND
Pokitto 52:c04087025cab 285 #endif //POK_ENABLE_SOUND
Pokitto 52:c04087025cab 286 #endif
Pokitto 52:c04087025cab 287 }
Pokitto 52:c04087025cab 288
Pokitto 52:c04087025cab 289 void Sound::playTrack(const uint16_t* track, uint8_t channel){
Pokitto 52:c04087025cab 290 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 291 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 292 return;
Pokitto 52:c04087025cab 293 stopTrack(channel);
Pokitto 52:c04087025cab 294 trackCursor[channel] = 0;
Pokitto 52:c04087025cab 295 trackData[channel] = (uint16_t*)track;
Pokitto 52:c04087025cab 296 trackIsPlaying[channel] = true;
Pokitto 52:c04087025cab 297 #endif
Pokitto 52:c04087025cab 298 }
Pokitto 52:c04087025cab 299
Pokitto 52:c04087025cab 300 void Sound::stopTrack(uint8_t channel){
Pokitto 52:c04087025cab 301 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 302 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 303 return;
Pokitto 52:c04087025cab 304 trackIsPlaying[channel] = false;
Pokitto 52:c04087025cab 305 stopPattern(channel);
Pokitto 52:c04087025cab 306 #endif
Pokitto 52:c04087025cab 307 }
Pokitto 52:c04087025cab 308
Pokitto 52:c04087025cab 309 void Sound::stopTrack(){
Pokitto 52:c04087025cab 310 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 311 for(uint8_t i=0; i<NUM_CHANNELS; i++){
Pokitto 52:c04087025cab 312 stopTrack(i);
Pokitto 52:c04087025cab 313 }
Pokitto 52:c04087025cab 314 #endif
Pokitto 52:c04087025cab 315 }
Pokitto 52:c04087025cab 316
Pokitto 52:c04087025cab 317 void Sound::updateTrack(uint8_t channel){
Pokitto 52:c04087025cab 318 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 319 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 320 return;
Pokitto 52:c04087025cab 321 if(trackIsPlaying[channel] && !patternIsPlaying[channel]){
Pokitto 52:c04087025cab 322 uint16_t data = pgm_read_word(trackData[channel] + trackCursor[channel]);
Pokitto 52:c04087025cab 323 if(data == 0xFFFF){ //en of the track
Pokitto 52:c04087025cab 324 trackIsPlaying[channel] = false;
Pokitto 52:c04087025cab 325 return;
Pokitto 52:c04087025cab 326 }
Pokitto 52:c04087025cab 327 uint8_t patternID = data & 0xFF;
Pokitto 52:c04087025cab 328 data >>= 8;
Pokitto 52:c04087025cab 329 patternPitch[channel] = data;
Pokitto 52:c04087025cab 330 playPattern((const uint16_t*)pgm_read_word(&(patternSet[channel][patternID])), channel);
Pokitto 52:c04087025cab 331 trackCursor[channel] ++;
Pokitto 52:c04087025cab 332 }
Pokitto 52:c04087025cab 333 #endif
Pokitto 52:c04087025cab 334 }
Pokitto 52:c04087025cab 335
Pokitto 52:c04087025cab 336 void Sound::updateTrack(){
Pokitto 52:c04087025cab 337 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 338 for (uint8_t i=0; i<NUM_CHANNELS; i++){
Pokitto 52:c04087025cab 339 updateTrack(i);
Pokitto 52:c04087025cab 340 }
Pokitto 52:c04087025cab 341 #endif
Pokitto 52:c04087025cab 342 }
Pokitto 52:c04087025cab 343
Pokitto 52:c04087025cab 344 void Sound::changePatternSet(const uint16_t* const* patterns, uint8_t channel){
Pokitto 52:c04087025cab 345 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 346 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 347 return;
Pokitto 52:c04087025cab 348 patternSet[channel] = (uint16_t**)patterns;
Pokitto 52:c04087025cab 349 #endif
Pokitto 52:c04087025cab 350 }
Pokitto 52:c04087025cab 351
Pokitto 52:c04087025cab 352 void Sound::playPattern(const uint16_t* pattern, uint8_t channel){
Pokitto 52:c04087025cab 353 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 354 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 355 return;
Pokitto 52:c04087025cab 356 stopPattern(channel);
Pokitto 52:c04087025cab 357 patternData[channel] = (uint16_t*)pattern;
Pokitto 52:c04087025cab 358 patternCursor[channel] = 0;
Pokitto 52:c04087025cab 359 patternIsPlaying[channel] = true;
Pokitto 52:c04087025cab 360 noteVolume[channel] = 9;
Pokitto 52:c04087025cab 361 //reinit commands
Pokitto 52:c04087025cab 362 volumeSlideStepDuration[channel] = 0;
Pokitto 52:c04087025cab 363 arpeggioStepDuration[channel] = 0;
Pokitto 52:c04087025cab 364 tremoloStepDuration[channel] = 0;
Pokitto 52:c04087025cab 365 #endif
Pokitto 52:c04087025cab 366 }
Pokitto 52:c04087025cab 367
Pokitto 52:c04087025cab 368 void Sound::updatePattern(){
Pokitto 52:c04087025cab 369 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 370 for (uint8_t i=0; i<NUM_CHANNELS; i++){
Pokitto 52:c04087025cab 371 updatePattern(i);
Pokitto 52:c04087025cab 372 }
Pokitto 52:c04087025cab 373 #endif
Pokitto 52:c04087025cab 374 }
Pokitto 52:c04087025cab 375
Pokitto 52:c04087025cab 376 void Sound::changeInstrumentSet(const uint16_t* const* instruments, uint8_t channel){
Pokitto 52:c04087025cab 377 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 378 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 379 return;
Pokitto 52:c04087025cab 380 instrumentSet[channel] = (uint16_t**)instruments;
Pokitto 52:c04087025cab 381 #endif
Pokitto 52:c04087025cab 382 }
Pokitto 52:c04087025cab 383
Pokitto 52:c04087025cab 384 void Sound::updatePattern(uint8_t i){
Pokitto 52:c04087025cab 385 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 386 if(i>=NUM_CHANNELS)
Pokitto 52:c04087025cab 387 return;
Pokitto 52:c04087025cab 388 if(patternIsPlaying[i]){
Pokitto 52:c04087025cab 389 if(noteDuration[i]==0){//if the end of the previous note is reached
Pokitto 52:c04087025cab 390
Pokitto 52:c04087025cab 391 uint16_t data = pgm_read_word(patternCursor[i] + patternData[i]);
Pokitto 52:c04087025cab 392
Pokitto 52:c04087025cab 393 if(data == 0){ //end of the pattern reached
Pokitto 52:c04087025cab 394 if(patternLooping[i] == true){
Pokitto 52:c04087025cab 395 patternCursor[i] = 0;
Pokitto 52:c04087025cab 396 data = pgm_read_word(patternCursor[i] + patternData[i]);
Pokitto 52:c04087025cab 397 }
Pokitto 52:c04087025cab 398 else{
Pokitto 52:c04087025cab 399 patternIsPlaying[i] = false;
Pokitto 52:c04087025cab 400 if(trackIsPlaying[i]){ //if this pattern is part of a track, get the next pattern
Pokitto 52:c04087025cab 401 updateTrack(i);
Pokitto 52:c04087025cab 402 data = pgm_read_word(patternCursor[i] + patternData[i]);
Pokitto 52:c04087025cab 403 } else {
Pokitto 52:c04087025cab 404 stopNote(i);
Pokitto 52:c04087025cab 405 //Serial.print("pattern end\n");
Pokitto 52:c04087025cab 406 return;
Pokitto 52:c04087025cab 407 }
Pokitto 52:c04087025cab 408 }
Pokitto 52:c04087025cab 409 }
Pokitto 52:c04087025cab 410
Pokitto 52:c04087025cab 411 while (data & 0x0001){ //read all commands and instrument changes
Pokitto 52:c04087025cab 412 data >>= 2;
Pokitto 52:c04087025cab 413 //Serial.print("\ncmd\t");
Pokitto 52:c04087025cab 414 uint8_t cmd = data & 0x0F;
Pokitto 52:c04087025cab 415 data >>= 4;
Pokitto 52:c04087025cab 416 uint8_t X = data & 0x1F;
Pokitto 52:c04087025cab 417 data >>= 5;
Pokitto 52:c04087025cab 418 int8_t Y = data - 16;
Pokitto 52:c04087025cab 419 command(cmd,X,Y,i);
Pokitto 52:c04087025cab 420 patternCursor[i]++;
Pokitto 52:c04087025cab 421 data = pgm_read_word(patternCursor[i] + patternData[i]);
Pokitto 52:c04087025cab 422 }
Pokitto 52:c04087025cab 423 data >>= 2;
Pokitto 52:c04087025cab 424
Pokitto 52:c04087025cab 425 uint8_t pitch = data & 0x003F;
Pokitto 52:c04087025cab 426 data >>= 6;
Pokitto 52:c04087025cab 427
Pokitto 52:c04087025cab 428 uint8_t duration = data;
Pokitto 52:c04087025cab 429 if(pitch != 63){
Pokitto 52:c04087025cab 430 }
Pokitto 52:c04087025cab 431
Pokitto 52:c04087025cab 432 playNote(pitch, duration, i);
Pokitto 52:c04087025cab 433
Pokitto 52:c04087025cab 434 patternCursor[i]++;
Pokitto 52:c04087025cab 435 }
Pokitto 52:c04087025cab 436 }
Pokitto 52:c04087025cab 437 #endif
Pokitto 52:c04087025cab 438 }
Pokitto 52:c04087025cab 439
Pokitto 52:c04087025cab 440 void Sound::stopPattern(uint8_t channel){
Pokitto 52:c04087025cab 441 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 442 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 443 return;
Pokitto 52:c04087025cab 444 stopNote(channel);
Pokitto 52:c04087025cab 445 patternIsPlaying[channel] = false;
Pokitto 52:c04087025cab 446 #endif
Pokitto 52:c04087025cab 447 }
Pokitto 52:c04087025cab 448
Pokitto 52:c04087025cab 449 void Sound::stopPattern(){
Pokitto 52:c04087025cab 450 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 451 for(uint8_t i=0; i<NUM_CHANNELS; i++){
Pokitto 52:c04087025cab 452 stopPattern(i);
Pokitto 52:c04087025cab 453 }
Pokitto 52:c04087025cab 454 #endif
Pokitto 52:c04087025cab 455 }
Pokitto 52:c04087025cab 456
Pokitto 52:c04087025cab 457 void Sound::command(uint8_t cmd, uint8_t X, int8_t Y, uint8_t i){
Pokitto 52:c04087025cab 458 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 459 if(i>=NUM_CHANNELS)
Pokitto 52:c04087025cab 460 return;
Pokitto 52:c04087025cab 461 switch(cmd){
Pokitto 52:c04087025cab 462 case CMD_VOLUME: //volume
Pokitto 52:c04087025cab 463 X = constrain((int8_t)X, 0, 10);
Pokitto 52:c04087025cab 464 noteVolume[i] = X;
Pokitto 52:c04087025cab 465 break;
Pokitto 52:c04087025cab 466 case CMD_INSTRUMENT: //instrument
Pokitto 52:c04087025cab 467 instrumentData[i] = (uint16_t*)pgm_read_word(&(instrumentSet[i][X]));
Pokitto 52:c04087025cab 468 instrumentLength[i] = pgm_read_word(&(instrumentData[i][0])) & 0x00FF; //8 LSB
Pokitto 52:c04087025cab 469 instrumentLength[i] *= prescaler;
Pokitto 52:c04087025cab 470 instrumentLooping[i] = min2((pgm_read_word(&(instrumentData[i][0])) >> 8), instrumentLength[i]); //8 MSB - check that the loop is shorter than the instrument length
Pokitto 52:c04087025cab 471 instrumentLooping[i] *= prescaler;
Pokitto 52:c04087025cab 472 break;
Pokitto 52:c04087025cab 473 case CMD_SLIDE: //volume slide
Pokitto 52:c04087025cab 474 volumeSlideStepDuration[i] = X * prescaler;
Pokitto 52:c04087025cab 475 volumeSlideStepSize[i] = Y;
Pokitto 52:c04087025cab 476 break;
Pokitto 52:c04087025cab 477 case CMD_ARPEGGIO:
Pokitto 52:c04087025cab 478 arpeggioStepDuration[i] = X * prescaler;
Pokitto 52:c04087025cab 479 arpeggioStepSize[i] = Y;
Pokitto 52:c04087025cab 480 break;
Pokitto 52:c04087025cab 481 case CMD_TREMOLO:
Pokitto 52:c04087025cab 482 tremoloStepDuration[i] = X * prescaler;
Pokitto 52:c04087025cab 483 tremoloStepSize[i] = Y;
Pokitto 52:c04087025cab 484 break;
Pokitto 52:c04087025cab 485 default:
Pokitto 52:c04087025cab 486 break;
Pokitto 52:c04087025cab 487 }
Pokitto 52:c04087025cab 488 #endif
Pokitto 52:c04087025cab 489 }
Pokitto 52:c04087025cab 490
Pokitto 52:c04087025cab 491 void Sound::playNote(uint8_t pitch, uint8_t duration, uint8_t channel){
Pokitto 52:c04087025cab 492 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 493 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 494 return;
Pokitto 52:c04087025cab 495 //set note
Pokitto 52:c04087025cab 496 notePitch[channel] = pitch;
Pokitto 52:c04087025cab 497 noteDuration[channel] = duration * prescaler;
Pokitto 52:c04087025cab 498 //reinit vars
Pokitto 52:c04087025cab 499 instrumentNextChange[channel] = 0;
Pokitto 52:c04087025cab 500 instrumentCursor[channel] = 0;
Pokitto 52:c04087025cab 501 notePlaying[channel] = true;
Pokitto 52:c04087025cab 502 _chanState[channel] = true;
Pokitto 52:c04087025cab 503 commandsCounter[channel] = 0;
Pokitto 52:c04087025cab 504 #endif
Pokitto 52:c04087025cab 505 }
Pokitto 52:c04087025cab 506
Pokitto 52:c04087025cab 507 void Sound::stopNote(uint8_t channel) {
Pokitto 52:c04087025cab 508 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 509 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 510 return;
Pokitto 52:c04087025cab 511 notePlaying[channel] = false;
Pokitto 52:c04087025cab 512 //counters
Pokitto 52:c04087025cab 513 noteDuration[channel] = 0;
Pokitto 52:c04087025cab 514 instrumentCursor[channel] = 0;
Pokitto 52:c04087025cab 515 commandsCounter[channel] = 0;
Pokitto 52:c04087025cab 516 //output
Pokitto 52:c04087025cab 517 _chanOutput[channel] = 0;
Pokitto 52:c04087025cab 518 _chanOutputVolume[channel] = 0;
Pokitto 52:c04087025cab 519 _chanState[channel] = false;
Pokitto 52:c04087025cab 520 updateOutput();
Pokitto 52:c04087025cab 521 #endif
Pokitto 52:c04087025cab 522 }
Pokitto 52:c04087025cab 523
Pokitto 52:c04087025cab 524 void Sound::stopNote() {
Pokitto 52:c04087025cab 525 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 526 for (uint8_t channel = 0; channel < NUM_CHANNELS; channel++) {
Pokitto 52:c04087025cab 527 stopNote(channel);
Pokitto 52:c04087025cab 528 }
Pokitto 52:c04087025cab 529 #endif
Pokitto 52:c04087025cab 530 }
Pokitto 52:c04087025cab 531
Pokitto 52:c04087025cab 532 void Sound::updateNote() {
Pokitto 52:c04087025cab 533 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 534 for (uint8_t i = 0; i < NUM_CHANNELS; i++) {
Pokitto 52:c04087025cab 535 updateNote(i);
Pokitto 52:c04087025cab 536 }
Pokitto 52:c04087025cab 537 #endif
Pokitto 52:c04087025cab 538 }
Pokitto 52:c04087025cab 539
Pokitto 52:c04087025cab 540 void Sound::updateNote(uint8_t i) {
Pokitto 52:c04087025cab 541 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 542 if(i>=NUM_CHANNELS)
Pokitto 52:c04087025cab 543 return;
Pokitto 52:c04087025cab 544 if (notePlaying[i]) {
Pokitto 52:c04087025cab 545
Pokitto 52:c04087025cab 546 if(noteDuration[i] == 0){
Pokitto 52:c04087025cab 547 stopNote(i);
Pokitto 52:c04087025cab 548 //Serial.println("note end");
Pokitto 52:c04087025cab 549 return;
Pokitto 52:c04087025cab 550 } else {
Pokitto 52:c04087025cab 551 noteDuration[i]--;
Pokitto 52:c04087025cab 552 }
Pokitto 52:c04087025cab 553
Pokitto 52:c04087025cab 554 if (instrumentNextChange[i] == 0) {
Pokitto 52:c04087025cab 555
Pokitto 52:c04087025cab 556 //read the step data from the progmem and decode it
Pokitto 52:c04087025cab 557 uint16_t thisStep = pgm_read_word(&(instrumentData[i][1 + instrumentCursor[i]]));
Pokitto 52:c04087025cab 558
Pokitto 52:c04087025cab 559 stepVolume[i] = thisStep & 0x0007;
Pokitto 52:c04087025cab 560 thisStep >>= 3;
Pokitto 52:c04087025cab 561
Pokitto 52:c04087025cab 562 uint8_t stepNoise = thisStep & 0x0001;
Pokitto 52:c04087025cab 563 thisStep >>= 1;
Pokitto 52:c04087025cab 564
Pokitto 52:c04087025cab 565 uint8_t stepDuration = thisStep & 0x003F;
Pokitto 52:c04087025cab 566 thisStep >>= 6;
Pokitto 52:c04087025cab 567
Pokitto 52:c04087025cab 568 stepPitch[i] = thisStep;
Pokitto 52:c04087025cab 569
Pokitto 52:c04087025cab 570 //apply the step settings
Pokitto 52:c04087025cab 571 instrumentNextChange[i] = stepDuration * prescaler;
Pokitto 52:c04087025cab 572
Pokitto 52:c04087025cab 573 _chanNoise[i] = stepNoise;
Pokitto 52:c04087025cab 574
Pokitto 52:c04087025cab 575
Pokitto 52:c04087025cab 576 instrumentCursor[i]++;
Pokitto 52:c04087025cab 577
Pokitto 52:c04087025cab 578 if (instrumentCursor[i] >= instrumentLength[i]) {
Pokitto 52:c04087025cab 579 if (instrumentLooping[i]) {
Pokitto 52:c04087025cab 580 instrumentCursor[i] = instrumentLength[i] - instrumentLooping[i];
Pokitto 52:c04087025cab 581 } else {
Pokitto 52:c04087025cab 582 stopNote(i);
Pokitto 52:c04087025cab 583 }
Pokitto 52:c04087025cab 584 }
Pokitto 52:c04087025cab 585 }
Pokitto 52:c04087025cab 586 instrumentNextChange[i]--;
Pokitto 52:c04087025cab 587
Pokitto 52:c04087025cab 588 commandsCounter[i]++;
Pokitto 52:c04087025cab 589
Pokitto 52:c04087025cab 590 //UPDATE VALUES
Pokitto 52:c04087025cab 591 //pitch
Pokitto 52:c04087025cab 592 outputPitch[i] = notePitch[i] + stepPitch[i] + patternPitch[i];
Pokitto 52:c04087025cab 593 if(arpeggioStepDuration[i]){
Pokitto 52:c04087025cab 594 outputPitch[i] += commandsCounter[i] / arpeggioStepDuration[i] * arpeggioStepSize[i];
Pokitto 52:c04087025cab 595 }
Pokitto 52:c04087025cab 596 outputPitch[i] = (outputPitch[i] + NUM_PITCH) % NUM_PITCH; //wrap
Pokitto 52:c04087025cab 597 //volume
Pokitto 52:c04087025cab 598 outputVolume[i] = noteVolume[i];
Pokitto 52:c04087025cab 599 if(volumeSlideStepDuration[i]){
Pokitto 52:c04087025cab 600 outputVolume[i] += commandsCounter[i] / volumeSlideStepDuration[i] * volumeSlideStepSize[i];
Pokitto 52:c04087025cab 601 }
Pokitto 52:c04087025cab 602 if(tremoloStepDuration[i]){
Pokitto 52:c04087025cab 603 outputVolume[i] += ((commandsCounter[i]/tremoloStepDuration[i]) % 2) * tremoloStepSize[i];
Pokitto 52:c04087025cab 604 }
Pokitto 52:c04087025cab 605 outputVolume[i] = constrain(outputVolume[i], 0, 9);
Pokitto 52:c04087025cab 606 if(notePitch[i] == 63){
Pokitto 52:c04087025cab 607 outputVolume[i] = 0;
Pokitto 52:c04087025cab 608 }
Pokitto 52:c04087025cab 609 // jonnehw noInterrupts();
Pokitto 52:c04087025cab 610 _chanHalfPeriod[i] = pgm_read_byte(_halfPeriods + outputPitch[i]);
Pokitto 52:c04087025cab 611 _chanOutput[i] = _chanOutputVolume[i] = outputVolume[i] * (globalVolume>>GLOBVOL_SHIFT) * chanVolumes[i] * stepVolume[i];
Pokitto 52:c04087025cab 612 //Serial.println(outputVolume[i]);
Pokitto 52:c04087025cab 613 // jonnehw interrupts();
Pokitto 52:c04087025cab 614 }
Pokitto 52:c04087025cab 615 #endif
Pokitto 52:c04087025cab 616 }
Pokitto 52:c04087025cab 617
Pokitto 52:c04087025cab 618 void Sound::setChannelHalfPeriod(uint8_t channel, uint8_t halfPeriod) {
Pokitto 52:c04087025cab 619 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 620 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 621 return;
Pokitto 52:c04087025cab 622 _chanHalfPeriod[channel] = halfPeriod;
Pokitto 52:c04087025cab 623 _chanState[channel] = false;
Pokitto 52:c04087025cab 624 _chanCount[channel] = 0;
Pokitto 52:c04087025cab 625 updateOutput();
Pokitto 52:c04087025cab 626 #endif
Pokitto 52:c04087025cab 627 }
Pokitto 52:c04087025cab 628
Pokitto 52:c04087025cab 629
Pokitto 52:c04087025cab 630 void Sound::generateOutput() {
Pokitto 52:c04087025cab 631 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 632 bool outputChanged = false;
Pokitto 52:c04087025cab 633 //no for loop here, for the performance sake (this function runs 15 000 times per second...)
Pokitto 52:c04087025cab 634 //CHANNEL 0
Pokitto 52:c04087025cab 635 if (_chanOutputVolume[0]) {
Pokitto 52:c04087025cab 636 _chanCount[0]++;
Pokitto 52:c04087025cab 637 if (_chanCount[0] >= _chanHalfPeriod[0]) {
Pokitto 52:c04087025cab 638 outputChanged = true;
Pokitto 52:c04087025cab 639 _chanState[0] = !_chanState[0];
Pokitto 52:c04087025cab 640 _chanCount[0] = 0;
Pokitto 52:c04087025cab 641 if (_chanNoise[0]) {
Pokitto 52:c04087025cab 642 _rand = 67 * _rand + 71;
Pokitto 52:c04087025cab 643 _chanOutput[0] = _rand % _chanOutputVolume[0];
Pokitto 52:c04087025cab 644 }
Pokitto 52:c04087025cab 645 }
Pokitto 52:c04087025cab 646 }
Pokitto 52:c04087025cab 647
Pokitto 52:c04087025cab 648
Pokitto 52:c04087025cab 649 //CHANNEL 1
Pokitto 52:c04087025cab 650 #if (NUM_CHANNELS > 1)
Pokitto 52:c04087025cab 651 if (_chanOutputVolume[1]) {
Pokitto 52:c04087025cab 652 _chanCount[1]++;
Pokitto 52:c04087025cab 653 if (_chanCount[1] >= _chanHalfPeriod[1]) {
Pokitto 52:c04087025cab 654 outputChanged = true;
Pokitto 52:c04087025cab 655 _chanState[1] = !_chanState[1];
Pokitto 52:c04087025cab 656 _chanCount[1] = 0;
Pokitto 52:c04087025cab 657 if (_chanNoise[1]) {
Pokitto 52:c04087025cab 658 _rand = 67 * _rand + 71;
Pokitto 52:c04087025cab 659 _chanOutput[1] = _rand % _chanOutputVolume[1];
Pokitto 52:c04087025cab 660 }
Pokitto 52:c04087025cab 661 }
Pokitto 52:c04087025cab 662 }
Pokitto 52:c04087025cab 663 #endif
Pokitto 52:c04087025cab 664
Pokitto 52:c04087025cab 665 //CHANNEL 2
Pokitto 52:c04087025cab 666 #if (NUM_CHANNELS > 2)
Pokitto 52:c04087025cab 667 if (_chanOutputVolume[2]) {
Pokitto 52:c04087025cab 668 _chanCount[2]++;
Pokitto 52:c04087025cab 669 if (_chanCount[2] >= _chanHalfPeriod[2]) {
Pokitto 52:c04087025cab 670 outputChanged = true;
Pokitto 52:c04087025cab 671 _chanState[2] = !_chanState[2];
Pokitto 52:c04087025cab 672 _chanCount[2] = 0;
Pokitto 52:c04087025cab 673 if (_chanNoise[2]) {
Pokitto 52:c04087025cab 674 _rand = 67 * _rand + 71;
Pokitto 52:c04087025cab 675 _chanOutput[2] = _rand % _chanOutputVolume[2];
Pokitto 52:c04087025cab 676 }
Pokitto 52:c04087025cab 677 }
Pokitto 52:c04087025cab 678 }
Pokitto 52:c04087025cab 679 #endif
Pokitto 52:c04087025cab 680
Pokitto 52:c04087025cab 681 //CHANNEL 3
Pokitto 52:c04087025cab 682 #if (NUM_CHANNELS > 3)
Pokitto 52:c04087025cab 683 if (_chanOutputVolume[3]) {
Pokitto 52:c04087025cab 684 _chanCount[3]++;
Pokitto 52:c04087025cab 685 if (_chanCount[3] >= _chanHalfPeriod[3]) {
Pokitto 52:c04087025cab 686 outputChanged = true;
Pokitto 52:c04087025cab 687 _chanState[3] = !_chanState[3];
Pokitto 52:c04087025cab 688 _chanCount[3] = 0;
Pokitto 52:c04087025cab 689 if (_chanNoise[3]) {
Pokitto 52:c04087025cab 690 _rand = 67 * _rand + 71;
Pokitto 52:c04087025cab 691 _chanOutput[3] = _rand % _chanOutputVolume[3];
Pokitto 52:c04087025cab 692 }
Pokitto 52:c04087025cab 693 }
Pokitto 52:c04087025cab 694 }
Pokitto 52:c04087025cab 695 #endif
Pokitto 52:c04087025cab 696
Pokitto 52:c04087025cab 697 #if POK_STREAMING_MUSIC
Pokitto 52:c04087025cab 698 if (streamstep) {
Pokitto 52:c04087025cab 699 outputChanged=true;
Pokitto 52:c04087025cab 700 }
Pokitto 52:c04087025cab 701 #endif
Pokitto 52:c04087025cab 702
Pokitto 52:c04087025cab 703 if (outputChanged) {
Pokitto 52:c04087025cab 704 updateOutput();
Pokitto 52:c04087025cab 705 }
Pokitto 52:c04087025cab 706 #endif
Pokitto 52:c04087025cab 707 }
Pokitto 52:c04087025cab 708
Pokitto 52:c04087025cab 709 void Sound::updateOutput() {
Pokitto 52:c04087025cab 710 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 711 uint32_t output = 0;
Pokitto 52:c04087025cab 712
Pokitto 52:c04087025cab 713 //CHANNEL 0
Pokitto 52:c04087025cab 714 if (_chanState[0]) {
Pokitto 52:c04087025cab 715 output += _chanOutput[0];
Pokitto 52:c04087025cab 716 }
Pokitto 52:c04087025cab 717
Pokitto 52:c04087025cab 718 //CHANNEL 1
Pokitto 52:c04087025cab 719 #if (NUM_CHANNELS > 1)
Pokitto 52:c04087025cab 720 if (_chanState[1]) {
Pokitto 52:c04087025cab 721 output += _chanOutput[1];
Pokitto 52:c04087025cab 722 }
Pokitto 52:c04087025cab 723 #endif
Pokitto 52:c04087025cab 724
Pokitto 52:c04087025cab 725 //CHANNEL 2
Pokitto 52:c04087025cab 726 #if (NUM_CHANNELS > 2)
Pokitto 52:c04087025cab 727 if (_chanState[2]) {
Pokitto 52:c04087025cab 728 output += _chanOutput[2];
Pokitto 52:c04087025cab 729 }
Pokitto 52:c04087025cab 730 #endif
Pokitto 52:c04087025cab 731
Pokitto 52:c04087025cab 732 //CHANNEL 3
Pokitto 52:c04087025cab 733 #if (NUM_CHANNELS > 3)
Pokitto 52:c04087025cab 734 if (_chanState[3]) {
Pokitto 52:c04087025cab 735 output += _chanOutput[3];
Pokitto 52:c04087025cab 736 }
Pokitto 52:c04087025cab 737 #endif
Pokitto 52:c04087025cab 738
Pokitto 52:c04087025cab 739 #ifndef POK_SIM
Pokitto 52:c04087025cab 740 #if POK_ENABLE_SOUND
Pokitto 52:c04087025cab 741 /** HARDWARE **/
Pokitto 52:c04087025cab 742
Pokitto 52:c04087025cab 743 #if POK_STREAMING_MUSIC
Pokitto 52:c04087025cab 744 if (streamstep) {
Pokitto 52:c04087025cab 745 //pwmout_write(&audiopwm,(float)(sbyte>>headPhoneLevel)/(float)255);
Pokitto 52:c04087025cab 746 sbyte *= discrete_vol_multipliers[discrete_vol];
Pokitto 52:c04087025cab 747 sbyte >>= 8;
Pokitto 52:c04087025cab 748 pwmout_write(&audiopwm,(float)(sbyte)/(float)255);
Pokitto 52:c04087025cab 749 }
Pokitto 52:c04087025cab 750 #endif
Pokitto 52:c04087025cab 751 output *= discrete_vol_multipliers[discrete_vol];
Pokitto 52:c04087025cab 752 output >>= 8;
Pokitto 52:c04087025cab 753 dac_write((uint8_t)output); //direct hardware mixing baby !
Pokitto 52:c04087025cab 754 soundbyte = output;
Pokitto 52:c04087025cab 755 #endif //POK_ENABLE_SOUND
Pokitto 52:c04087025cab 756 #else
Pokitto 52:c04087025cab 757 /** SIMULATOR **/
Pokitto 52:c04087025cab 758 #if POK_STREAMING_MUSIC
Pokitto 52:c04087025cab 759 if (streamstep) {
Pokitto 52:c04087025cab 760 uint16_t o = output + sbyte;
Pokitto 52:c04087025cab 761 output = (o/2);//>>headPhoneLevel;
Pokitto 52:c04087025cab 762 }
Pokitto 52:c04087025cab 763 #endif
Pokitto 52:c04087025cab 764 soundbyte = output;//<<headPhoneLevel;
Pokitto 52:c04087025cab 765 #endif // POK_SIM
Pokitto 52:c04087025cab 766 #endif
Pokitto 52:c04087025cab 767 }
Pokitto 52:c04087025cab 768
Pokitto 52:c04087025cab 769 void Sound::setPatternLooping(bool loop, uint8_t channel) {
Pokitto 52:c04087025cab 770 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 771 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 772 return;
Pokitto 52:c04087025cab 773 patternLooping[channel] = loop;
Pokitto 52:c04087025cab 774 #endif
Pokitto 52:c04087025cab 775 }
Pokitto 52:c04087025cab 776
Pokitto 52:c04087025cab 777 void Sound::playOK(){
Pokitto 52:c04087025cab 778 #if POK_GBSOUND
Pokitto 52:c04087025cab 779 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 780 playPattern(playOKPattern,0);
Pokitto 52:c04087025cab 781 #endif
Pokitto 52:c04087025cab 782 #endif // POK_GBSOUND
Pokitto 52:c04087025cab 783 }
Pokitto 52:c04087025cab 784
Pokitto 52:c04087025cab 785 void Sound::playCancel(){
Pokitto 52:c04087025cab 786 #if POK_GBSOUND
Pokitto 52:c04087025cab 787 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 788 playPattern(playCancelPattern,0);
Pokitto 52:c04087025cab 789 #endif
Pokitto 52:c04087025cab 790 #endif
Pokitto 52:c04087025cab 791 }
Pokitto 52:c04087025cab 792
Pokitto 52:c04087025cab 793 void Sound::playTick(){
Pokitto 52:c04087025cab 794 #if POK_GBSOUND
Pokitto 52:c04087025cab 795 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 796 playPattern(playTickP,0);
Pokitto 52:c04087025cab 797 #endif
Pokitto 52:c04087025cab 798 #endif // POK_GBSOUND
Pokitto 52:c04087025cab 799 }
Pokitto 52:c04087025cab 800
Pokitto 52:c04087025cab 801 void Sound::setVolume(int16_t volume) {
Pokitto 52:c04087025cab 802 //#if NUM_CHANNELS > 0
Pokitto 52:c04087025cab 803 if (volume<0) volume = 0;
Pokitto 52:c04087025cab 804 //if (volume>volumeMax) volume = volumeMax;
Pokitto 52:c04087025cab 805 globalVolume = volume;
Pokitto 52:c04087025cab 806 #if POK_ENABLE_SOUND > 0
Pokitto 52:c04087025cab 807 discrete_vol = (volume>>5);
Pokitto 52:c04087025cab 808 #ifndef POK_SIM
Pokitto 52:c04087025cab 809 setHWvolume(discrete_vol_hw_levels[discrete_vol]); //boost volume if headphonelevel
Pokitto 52:c04087025cab 810 #endif
Pokitto 52:c04087025cab 811 #endif
Pokitto 52:c04087025cab 812 #if POK_SHOW_VOLUME > 0
Pokitto 52:c04087025cab 813 _soundc.volbar_visible = VOLUMEBAR_TIMEOUT;
Pokitto 52:c04087025cab 814 #endif
Pokitto 52:c04087025cab 815 //#endif
Pokitto 52:c04087025cab 816 }
Pokitto 52:c04087025cab 817
Pokitto 52:c04087025cab 818 uint16_t Sound::getVolume() {
Pokitto 52:c04087025cab 819 //#if NUM_CHANNELS > 0
Pokitto 52:c04087025cab 820 return globalVolume;
Pokitto 52:c04087025cab 821 //#else
Pokitto 52:c04087025cab 822 // return 0;
Pokitto 52:c04087025cab 823 //#endif
Pokitto 52:c04087025cab 824 }
Pokitto 52:c04087025cab 825
Pokitto 52:c04087025cab 826 void Sound::setVolume(int8_t volume, uint8_t channel) {
Pokitto 52:c04087025cab 827 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 828 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 829 return;
Pokitto 52:c04087025cab 830 volume = (volume > VOLUME_CHANNEL_MAX) ? VOLUME_CHANNEL_MAX : volume;
Pokitto 52:c04087025cab 831 volume = (volume < 0) ? 0 : volume;
Pokitto 52:c04087025cab 832 chanVolumes[channel] = volume;
Pokitto 52:c04087025cab 833 #endif
Pokitto 52:c04087025cab 834 }
Pokitto 52:c04087025cab 835
Pokitto 52:c04087025cab 836 uint8_t Sound::getVolume(uint8_t channel) {
Pokitto 52:c04087025cab 837 #if(NUM_CHANNELS > 0)
Pokitto 52:c04087025cab 838 if(channel>=NUM_CHANNELS)
Pokitto 52:c04087025cab 839 return 255;
Pokitto 52:c04087025cab 840 return (chanVolumes[channel]);
Pokitto 52:c04087025cab 841 #else
Pokitto 52:c04087025cab 842 return 0;
Pokitto 52:c04087025cab 843 #endif
Pokitto 52:c04087025cab 844 }
Pokitto 52:c04087025cab 845
Pokitto 52:c04087025cab 846 void Sound::playTone(uint8_t os, int frq, uint8_t amp, uint8_t wav,uint8_t arpmode)
Pokitto 52:c04087025cab 847 {
Pokitto 52:c04087025cab 848 if (wav>5) wav=0;
Pokitto 52:c04087025cab 849 if (arpmode>MAX_ARPMODE) arpmode=MAX_ARPMODE;
Pokitto 52:c04087025cab 850 if (os==1) setOSC(&osc1,1,wav,1,0,0,frq,amp,0,0,0,0,0,0,arpmode,0,0);
Pokitto 52:c04087025cab 851 else if (os==2) setOSC(&osc2,1,wav,1,0,0,frq,amp,0,0,0,0,0,0,arpmode,0,0);
Pokitto 52:c04087025cab 852 else if (os==3) setOSC(&osc3,1,wav,1,0,0,frq,amp,0,0,0,0,0,0,arpmode,0,0);
Pokitto 52:c04087025cab 853 }
Pokitto 52:c04087025cab 854
Pokitto 52:c04087025cab 855 void Sound::playTone(uint8_t os, uint16_t frq, uint8_t volume, uint32_t duration)
Pokitto 52:c04087025cab 856 {
Pokitto 52:c04087025cab 857 if (os==1) setOSC(&osc1,1,WSQUARE,frq,volume,duration);
Pokitto 52:c04087025cab 858 else if (os==2) setOSC(&osc2,1,WTRI,frq,volume,duration);
Pokitto 52:c04087025cab 859 else if (os==3) setOSC(&osc3,1,WTRI,frq,volume,duration);
Pokitto 52:c04087025cab 860 }
Pokitto 52:c04087025cab 861
Pokitto 52:c04087025cab 862 uint8_t Sound::ampIsOn()
Pokitto 52:c04087025cab 863 {
Pokitto 52:c04087025cab 864 #ifdef POK_SIM
Pokitto 52:c04087025cab 865 return core.ampIsOn();
Pokitto 52:c04087025cab 866 #else
Pokitto 52:c04087025cab 867 #if POK_ENABLE_SOUND > 0
Pokitto 52:c04087025cab 868 return Pokitto::ampIsOn();
Pokitto 52:c04087025cab 869 #endif
Pokitto 52:c04087025cab 870 #endif // POK_SIM
Pokitto 52:c04087025cab 871 return 0;
Pokitto 52:c04087025cab 872 }
Pokitto 52:c04087025cab 873
Pokitto 52:c04087025cab 874 void Sound::ampEnable(uint8_t v) {
Pokitto 52:c04087025cab 875 #ifdef POK_SIM
Pokitto 52:c04087025cab 876 core.ampEnable(v);
Pokitto 52:c04087025cab 877 #else
Pokitto 52:c04087025cab 878 #if POK_ENABLE_SOUND > 0
Pokitto 52:c04087025cab 879 Pokitto::ampEnable(v);
Pokitto 52:c04087025cab 880 #endif
Pokitto 52:c04087025cab 881 #endif // POK_SIM
Pokitto 52:c04087025cab 882
Pokitto 52:c04087025cab 883 }
Pokitto 52:c04087025cab 884
Pokitto 52:c04087025cab 885 int Sound::playMusicStream(char* filename)
Pokitto 52:c04087025cab 886 {
Pokitto 52:c04087025cab 887 return playMusicStream(filename,FILE_MODE_READONLY | FILE_MODE_BINARY);
Pokitto 52:c04087025cab 888 }
Pokitto 52:c04087025cab 889
Pokitto 52:c04087025cab 890 int Sound::playMusicStream()
Pokitto 52:c04087025cab 891 {
Pokitto 52:c04087025cab 892 #if POK_STREAMING_MUSIC >0
Pokitto 52:c04087025cab 893 if (currentPtr) {
Pokitto 52:c04087025cab 894 pokPlayStream();
Pokitto 52:c04087025cab 895 return 1;
Pokitto 52:c04087025cab 896 } else return 0; //no stream
Pokitto 52:c04087025cab 897 #endif // POK_STREAMING_MUSIC
Pokitto 58:5f58a2846a20 898 return 0;
Pokitto 52:c04087025cab 899 }
Pokitto 52:c04087025cab 900
Pokitto 52:c04087025cab 901 void Sound::pauseMusicStream() {
Pokitto 52:c04087025cab 902 #if POK_ENABLE_SOUND > 0
Pokitto 52:c04087025cab 903 pokPauseStream();
Pokitto 52:c04087025cab 904 #endif
Pokitto 52:c04087025cab 905 }
Pokitto 52:c04087025cab 906
Pokitto 52:c04087025cab 907 int Sound::playMusicStream(char* filename, uint8_t options)
Pokitto 52:c04087025cab 908 {
Pokitto 52:c04087025cab 909 #if POK_STREAMING_MUSIC
Pokitto 52:c04087025cab 910 uint8_t result;
Pokitto 52:c04087025cab 911 result = pokInitSD();
Pokitto 52:c04087025cab 912 if (!isThisFileOpen(filename)) {
Pokitto 52:c04087025cab 913 fileClose(); // close any open files
Pokitto 52:c04087025cab 914 result = fileOpen(filename,FILE_MODE_READONLY | FILE_MODE_BINARY);
Pokitto 52:c04087025cab 915 }
Pokitto 52:c04087025cab 916
Pokitto 52:c04087025cab 917 if (result) {
Pokitto 52:c04087025cab 918 currentPtr = 0; // mark that no stream is available
Pokitto 52:c04087025cab 919 return 0; // opening music file failed
Pokitto 52:c04087025cab 920 }
Pokitto 52:c04087025cab 921
Pokitto 52:c04087025cab 922 fileReadBytes(&buffers[0][0],BUFFER_SIZE);
Pokitto 52:c04087025cab 923 fileReadBytes(&buffers[1][0],BUFFER_SIZE);
Pokitto 52:c04087025cab 924 fileReadBytes(&buffers[2][0],BUFFER_SIZE);
Pokitto 52:c04087025cab 925 fileReadBytes(&buffers[3][0],BUFFER_SIZE);
Pokitto 52:c04087025cab 926 currentBuffer = 0;
Pokitto 52:c04087025cab 927 currentPtr = buffers[currentBuffer];
Pokitto 52:c04087025cab 928 endPtr = currentPtr + BUFFER_SIZE;
Pokitto 52:c04087025cab 929
Pokitto 52:c04087025cab 930 //streaming = STR_PLAYING|options;
Pokitto 52:c04087025cab 931
Pokitto 52:c04087025cab 932 if (!options) pokPlayStream(); // activate stream
Pokitto 52:c04087025cab 933 #endif //POK_STREAMING_MUSIC
Pokitto 52:c04087025cab 934 return 1; // opening music file succeeded
Pokitto 52:c04087025cab 935 }
Pokitto 52:c04087025cab 936
Pokitto 52:c04087025cab 937 uint32_t Sound::getMusicStreamElapsedSec() {
Pokitto 52:c04087025cab 938 #if POK_STREAMING_MUSIC
Pokitto 52:c04087025cab 939 return streamcounter/POK_AUD_FREQ;
Pokitto 52:c04087025cab 940 #endif
Pokitto 52:c04087025cab 941 return 0;
Pokitto 52:c04087025cab 942 }
Pokitto 52:c04087025cab 943
Pokitto 52:c04087025cab 944 uint32_t Sound::getMusicStreamElapsedMilliSec() {
Pokitto 52:c04087025cab 945 #if POK_STREAMING_MUSIC
Pokitto 52:c04087025cab 946 return streamcounter/(POK_AUD_FREQ/1000);
Pokitto 52:c04087025cab 947 #endif
Pokitto 52:c04087025cab 948 return 0;
Pokitto 52:c04087025cab 949 }
Pokitto 52:c04087025cab 950