/********************************************************************** * Music Player for the ATMega8 * Uses all 3 timers for generating a 2voices, 1bit sound. * Copyright 2010, Adrien Destugues * Distributed under the terms of the MIT licence **********************************************************************/ #include #include #include #include #include #include #include #define C2_SoundOn() TCCR2 |= (1<>8)]); break; case 1: C1_SetFreq(Note2Reg[current.n]); break; case 2: C1_SetFreq(Note2Reg[current.n + (current.p&0xF)]); subtick = 0; break; } break; case V: C1_SetFreq(Note2Reg[current.n]-current.p/2+subtick%current.p); break; case T: if(subtick%current.p == 0) { C1_SoundOn(); C1_SetFreq(Note2Reg[current.n]); } else C1_SoundOff(); break; } // CHANNEL 2 ------------------------------- if (nexttime2 <= time) { current2 = song[step2]; step2++; subtick2 = 0; // Go to next step nexttime2 = time + current2.d; if(current2.f != 0) C2_SoundOn(); else C2_SoundOff(); // Test if song is finished, if so loop over if (current2.p == S && current2.d == 0) { step2 = 0; time = 0; nexttime2 = 1; } } subtick2++; switch (current2.f) { default: case N: C2_SetFreq(Note2Reg[current2.n]); break; case A: switch(subtick2) { case 0: C2_SetFreq(Note2Reg[current2.n + ((current2.p&0xF0)>>8)]); break; case 1: C2_SetFreq(Note2Reg[current2.n]); break; case 2: C2_SetFreq(Note2Reg[current2.n + (current2.p&0xF)]); subtick2 = 0; break; } break; case V: C2_SetFreq(Note2Reg[current2.n]-current2.p/2+subtick2%current2.p); break; case T: if(subtick2%current2.p == 0) { C2_SoundOn(); C2_SetFreq(Note2Reg[current2.n]); } else C2_SoundOff(); break; } time++; } } }