Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependents: YATTT sd_map_test cPong SnowDemo ... more
PokittoLib
Library for programming Pokitto hardware
How to Use
- Import this library to online compiler (see button "import" on the right hand side
- DO NOT import mbed-src anymore, a better version is now included inside PokittoLib
- Change My_settings.h according to your project
- Start coding!
Revision 66:6281a40d73e6, committed 2019-03-23
- Comitter:
- Pokitto
- Date:
- Sat Mar 23 20:03:34 2019 +0000
- Parent:
- 65:deed4aa606fb
- Child:
- 67:068fa6345036
- Child:
- 69:f9f49ff29720
- Commit message:
- Updated pokittolib to current embitz dev branch
Changed in this revision
--- a/POKITTO_CORE/GBcompatibility.h Sat Mar 23 19:22:35 2019 +0000 +++ b/POKITTO_CORE/GBcompatibility.h Sat Mar 23 20:03:34 2019 +0000 @@ -55,7 +55,7 @@ //SETTINGS YOU CAN EDIT -#define NUM_CHANNELS 1 //number of sound channels, between 0 and 4 +#define NUM_CHANNELS 3 //number of sound channels, between 0 and 4 #define DISPLAY_ROT NOROT //set to NOROT, ROTCCW, ROT180 or ROTCW. Can be used to play in portrait mode. #define ENABLE_GUI 1 //enable menu, keyboard, pop-up, volume adjust functions #define ENABLE_BITMAPS 1 //will replace bitmaps with rectangles if disabled
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/POKITTO_CORE/Localization.h Sat Mar 23 20:03:34 2019 +0000 @@ -0,0 +1,48 @@ +/**************************************************************************/ +/*! + @file Localization.h + @author Hannu Viitala + + @section LICENSE + + Software License Agreement (BSD License) + + Copyright (c) 2017, Jonne Valola + All rights reserved. + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions are met: + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + 3. Neither the name of the copyright holders nor the + names of its contributors may be used to endorse or promote products + derived from this software without specific prior written permission. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ''AS IS'' AND ANY + EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY + DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ +/**************************************************************************/ + +#ifndef LOCALIZATION_H +#define LOCALIZATION_H + +//** Localized strings of the Pokitto SW */ + +// Texts +#define STR_OK "OK" +#define STR_CANCEL "CANCEL" + +#endif + +
--- a/POKITTO_CORE/PokittoButtons.cpp Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_CORE/PokittoButtons.cpp Sat Mar 23 20:03:34 2019 +0000
@@ -126,8 +126,10 @@
* return true if 'button' is released
*/
bool Buttons::released(uint8_t button) {
- if (states[button] == 0xFF)
+ if (states[button] == 0xFF) {
+ states[button] = 0; // prevent continuous released state!
return true;
+ }
else
return false;
}
--- a/POKITTO_CORE/PokittoConsole.cpp Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_CORE/PokittoConsole.cpp Sat Mar 23 20:03:34 2019 +0000
@@ -180,6 +180,7 @@
_display->print("Hit:");break;
default:
return;
+ break;
}
switch (c.msgtype) {
--- a/POKITTO_CORE/PokittoCookie.cpp Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_CORE/PokittoCookie.cpp Sat Mar 23 20:03:34 2019 +0000
@@ -117,13 +117,15 @@
}
bool Cookie::saveCookie() {
- if (!_status || !_pointer) initialize(); //reinitialize if needed
- if (!_status || !_pointer) return false; //return if initialize still failed
+ if (!_status || !_pointer) return false; //return if not initialized
char* p = _pointer;
_head=0;
_block=0;
_block=findMyNextBlock();
for (int i=0; i<_datasize; i++) writeQueue(*p++);
+ #if POK_ENABLE_SOUND
+ Pokitto::soundInit(true); //re-init sound
+ #endif
return true;
}
@@ -151,7 +153,7 @@
int Cookie::exists(const char* idkey) {
for (int i=0; i< SBMAXKEYS; i++) {
- #ifndef POK_SIM
+
if(eeprom_read_byte((uint16_t*)(i*SBKEYSIZE))==idkey[0]) {
int total=0;
for (int j=0; j<SBKEYSIZE;j++) {
@@ -159,7 +161,7 @@
}
if (total==SBKEYSIZE) return i; // return the keyslot number where key exists
}
- #endif
+
}
return SBINVALIDSLOT; //not found
}
@@ -167,9 +169,9 @@
int Cookie::getFreeKeytableSlot() {
int freeslot=SBINVALIDSLOT;
for (int i=0; i<SBMAXKEYS; i++) {
- #ifndef POK_SIM
+
if (eeprom_read_byte((uint16_t*)(i*SBKEYSIZE))==0) {freeslot=i; break;}
- #endif
+
}
return freeslot;
}
@@ -192,21 +194,21 @@
bool Cookie::isFreeBlock(int n) {
if (n>=SBMAXBLOCKS) return false;
- #ifndef POK_SIM
+
if (!(eeprom_read_byte((uint16_t*)(SBMAXKEYS*SBKEYSIZE+n))&0x80)) return true; //highest bit 0, its free
- #endif
+
return false; //its not free
}
bool Cookie::isMyBlock(int n) {
if (n>=SBMAXBLOCKS) return false;
if (isFreeBlock(n)) return false; //"free" blocks can not be "reserved" at the same time!
- #ifndef POK_SIM
+
char temp; int address;
address = (SBMAXKEYS*SBKEYSIZE+n);
temp = eeprom_read_byte((uint16_t*)address);
if ((temp&0x7F) ==_keyorder) return true;
- #endif
+
return false; //its not your block
}
@@ -214,21 +216,21 @@
if (n>=SBMAXBLOCKS) return false;
if (k>=SBMAXKEYS) return false;
if (isFreeBlock(n)) return false; //"free" blocks can not be "owned" by anyone
- #ifndef POK_SIM
+
char temp; int address;
address = (SBMAXKEYS*SBKEYSIZE+n);
temp = eeprom_read_byte((uint16_t*)address);
if ((temp&0x7F) == k) return true;
- #endif
+
return false; //its not your block
}
void Cookie::writeKeyToKeytable(const char* key, int slot) {
for (int i=0; i<SBKEYSIZE; i++) {
- #ifndef POK_SIM
+
if (key[i]) eeprom_write_byte((uint16_t*)(slot*SBKEYSIZE+i),key[i]);
else eeprom_write_byte((uint16_t*)(slot*SBKEYSIZE+i),0);
- #endif
+
}
}
@@ -236,63 +238,63 @@
answer[8]=0;
if (n >= SBMAXKEYS) n=SBMAXKEYS-1;
for (int i=0; i<SBKEYSIZE; i++) {
- #ifndef POK_SIM
+
answer[i] = eeprom_read_byte((uint16_t*)(n*SBKEYSIZE+i));
- #endif
+
}
}
char Cookie::getBlockTableEntry(int n) {
if (n>=SBMAXBLOCKS) return 0x80; // out of bounds will return a reserved block marker
- #ifndef POK_SIM
+
return eeprom_read_byte((uint16_t*)(SBKEYSIZE*SBMAXKEYS+n));
- #endif
- //return 0x80;
+
+ return 0x80;
}
void Cookie::readBlock(int n, char* data) {
for (int i=0; i<SBBLOCKSIZE; i++) {
data[i]=0;
- #ifndef POK_SIM
+
if (n < SBMAXBLOCKS) data[i] = eeprom_read_byte((uint16_t*)(SBKEYSIZE*SBMAXKEYS+SBMAXBLOCKS+n*SBBLOCKSIZE+i));
- #endif
+
}
}
void Cookie::formatKeytable() {
for (int j=0; j<SBMAXKEYS; j++) {
for (int i=0; i<SBKEYSIZE; i++) {
- #ifndef POK_SIM
+
eeprom_write_byte((uint16_t*)(j*SBKEYSIZE+i),0);
- #endif
+
}
}
}
void Cookie::freeBlock(int n) {
if (n >= SBMAXBLOCKS) return; //out of bounds
- #ifndef POK_SIM
+
// delete entry from blocktable
eeprom_write_byte((uint16_t*)(SBKEYSIZE*SBMAXKEYS+n),0);
- #endif
+
for (int i=0; i<SBBLOCKSIZE;i++) {
- #ifndef POK_SIM
+
// wipe data in the block
eeprom_write_byte((uint16_t*)(SBKEYSIZE*SBMAXKEYS+SBMAXBLOCKS+n*SBBLOCKSIZE+i),0);
- #endif
+
}
}
bool Cookie::reserveBlock() {
for (int i=0; i<SBMAXBLOCKS;i++) {
- #ifndef POK_SIM
+
// reserve block from blocktable
if (isFreeBlock(i)) {
//free block found, mark it for us in the blocktable
eeprom_write_byte((uint16_t*)(SBKEYSIZE*SBMAXKEYS+i),_keyorder | 0x80);
return true;
}
- #endif
+
}
return false; // no free block found
}
@@ -300,9 +302,9 @@
void Cookie::eraseKeytableEntry(int n) {
if (n >= SBMAXKEYS) n=SBMAXKEYS-1;
for (int i=0; i<SBKEYSIZE; i++) {
- #ifndef POK_SIM
+
eeprom_write_byte((uint16_t*)(n*SBKEYSIZE+i),0);
- #endif
+
}
}
@@ -331,11 +333,11 @@
char Cookie::readQueue() {
char data=0;
- #ifndef POK_SIM
+
int address;
address = SBMAXKEYS*SBKEYSIZE+SBMAXBLOCKS+SBBLOCKSIZE*_block+_head%SBBLOCKSIZE;
data=eeprom_read_byte((uint16_t*)address);
- #endif
+
_head++;
if (_head%SBBLOCKSIZE==0 && _head) {
_block++;
@@ -345,9 +347,9 @@
}
void Cookie::writeQueue(char data) {
- #ifndef POK_SIM
+
eeprom_write_byte((uint16_t*)(SBMAXKEYS*SBKEYSIZE+SBMAXBLOCKS+SBBLOCKSIZE*_block+_head%SBBLOCKSIZE),data);
- #endif
+
_head++;
if (_head%SBBLOCKSIZE==0 && _head) {
_block++;
--- a/POKITTO_CORE/PokittoCookie.h Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_CORE/PokittoCookie.h Sat Mar 23 20:03:34 2019 +0000
@@ -307,7 +307,7 @@
/** Keyorder
* order number of key in key table
*/
- char _keyorder;
+ unsigned char _keyorder;
/** Status
* false = uninitialized
--- a/POKITTO_CORE/PokittoCore.cpp Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_CORE/PokittoCore.cpp Sat Mar 23 20:03:34 2019 +0000
@@ -179,8 +179,8 @@
uint32_t counter=0;
uint8_t data[256];
/** prepare the flash writing **/
- //float progress=0;
- //int opg=-1;
+ float progress=0;
+ int opg=-1;
uint32_t fsize=0;
fileEnd(); //
fsize = fileGetPosition();
@@ -194,7 +194,7 @@
if (counter >= fsize) {
break;
}
- //opg=progress;
+ opg=progress;
if (fileReadBytes(&data[0],0x100)<0x100) {
if (fsize-counter>0x100) {
display.println("ERROR READING LOA.DER FILE");
@@ -271,7 +271,7 @@
display.println("LOADER IS NOT AVAILABLE ON THE SIMULATOR. PRESS A TO RETURN.");
#else
uint32_t* bootinfo;
- uint32_t sdversion=0, sdjump=0;
+ uint32_t bootversion=0, sdversion=0, sdjump=0;
bool flashloader=false, checkforboot=true;
//check for loa.der on SD card
#if POK_ENABLE_LOADER_UPDATES > 0
@@ -381,17 +381,17 @@
display.directcolor=COLOR_WHITE;
display.fontSize=2;
int countd = 0;
- #ifndef POK_SIM
+ //#ifndef POK_SIM
//read countdown time from settings
countd = eeprom_read_byte((uint16_t*)EESETTINGS_LOADERWAIT);
- #endif
+ //#endif
if (countd<=0 || countd > 5) countd=3;
uint16_t c2 = getTime();
while (countd) {
buttons.pollButtons();
display.set_cursor(13*8,15*8);
display.print(countd);
- if (getTime()>c2+1000) {
+ if (getTime()>uint32_t(c2+1000)) {
c2=getTime();
countd--;
}
@@ -465,42 +465,42 @@
#define VINCMULT 50
#endif //POK_SIM
void Core::setVolLimit() {
-
display.enableDirectPrinting(true);
display.adjustCharStep = 0;
//sound.setMaxVol(VOLUME_HEADPHONE_MAX);
int dstate=1;
bool wipe = true;
- float vol = sound.getVolume();
- #ifndef POK_SIM
+ float vol = sound.getVolume();
+ //#ifndef POK_SIM
vol=eeprom_read_byte((uint16_t*)EESETTINGS_VOL);
Pokitto::Sound::globalVolume=vol;
- #endif
+ //#endif
if (vol>VOLUME_HEADPHONE_MAX) sound.setMaxVol(VOLUME_SPEAKER_MAX);
else sound.setMaxVol(VOLUME_HEADPHONE_MAX);
#ifdef PRODUCTIONTESTING
vol=170;
sound.setMaxVol(VOLUME_SPEAKER_MAX);
#endif
- //sound.setVolume(0);
- //if (vol) {
- //for (uint8_t t=0;t<=vol;t++) sound.setVolume(t);
+ //for (uint8_t t=0;t<=vol;t++) {
+ // sound.setVolume(t);
//}
- discrete_vol = ((int)vol>>5); //get rid of 0 vol number
- sound.setVolume(vol);
+ sound.setVolume(vol/4);
+ sound.setVolume(vol/2);
+ sound.setVolume(vol); //prevent "crack" by gradually increasing volume
+ discrete_vol = ((int)vol>>5); // fix "shows zero" in volume slider bug
volbar_visible=0;
int countd=0;
- #ifndef POK_SIM
+ //#ifndef POK_SIM
//read countdown time from settings
- //countd = eeprom_read_byte((uint16_t*)EESETTINGS_VOLWAIT);
- #endif
+ countd = eeprom_read_byte((uint16_t*)EESETTINGS_VOLWAIT);
+ //#endif
if (countd<=0 || countd > 10) countd=0xFFFF;
#ifdef PRODUCTIONTESTING
countd=2;
#endif
uint16_t c2 = getTime();
while (core.isRunning() && dstate && countd){
- if (getTime()>c2+1000) {
+ if (getTime()>uint32_t(c2+1000)) {
c2=getTime();
if (countd<0xFFFF) countd--;
}
@@ -592,9 +592,9 @@
}
}
vol = sound.getVolume();
- #ifndef POK_SIM
+ //#ifndef POK_SIM
if (vol != eeprom_read_byte((uint16_t*)EESETTINGS_VOL)) eeprom_write_byte((uint16_t*)EESETTINGS_VOL,(uint8_t)vol);
- #endif
+ //#endif
sound.setVolume(vol);
//sound.volumeUp();
display.setCursor(0,0);
@@ -617,12 +617,22 @@
buttons.update();
battery.begin();
display.begin();
+
+ char logoFlag = eeprom_read_byte((uint16_t*)EESETTINGS_SKIPINTRO);
+ if( logoFlag&2 ){ // toggle flag set, change value for next boot
+ eeprom_write_byte((uint16_t*)EESETTINGS_SKIPINTRO, !(logoFlag&1));
+ }
+ logoFlag &= 1;
+
#if POK_DISPLAYLOGO
#if PROJ_DEVELOPER_MODE != 1
- showLogo();
+ if( logoFlag == 0 ){
+ showLogo();
+ }
#endif // PROJ_DEVELOPER_MODE
#endif // POK_DISPLAYLOGO
+
display.enableDirectPrinting(true);
display.directbgcolor = COLOR_BLACK;
display.clearLCD();
@@ -631,7 +641,6 @@
display.enableDirectPrinting(true);
display.directbgcolor = COLOR_BLACK;
display.directcolor = COLOR_GREEN;
- display.clearLCD();
display.setFont(fntC64UIGfx);
display.adjustCharStep=0;
display.adjustLineStep=1;
@@ -641,7 +650,9 @@
#ifndef DISABLE_LOADER
#if PROJ_DEVELOPER_MODE != 1
- askLoader();
+ if( logoFlag == 0 ){
+ askLoader();
+ }
#endif // PROJ_DEVELOPER_MODE
#endif
@@ -649,18 +660,22 @@
sound.setMaxVol(VOLUME_SPEAKER_MAX);
sound.setVolume(VOLUME_SPEAKER_MAX);
#else
- //showWarning();
- setVolLimit();
- display.clear();
- display.update();
+ if( logoFlag == 0 ){
+ //showWarning();
+ setVolLimit();
+ display.clear();
+ display.update();
- while(buttons.states[BTN_A])
- {
- buttons.update();
- }
+ while(buttons.states[BTN_A])
+ {
+ buttons.update();
+ }
+ }else{
+ sound.setVolume(sound.getVolume());//make sure we're at set volume before continue
+ }
- //sound.setVolume(sound.getVolume());//make sure we're at set volume before continue
#endif
+
display.enableDirectPrinting(false);
display.adjustCharStep=1;
display.adjustLineStep=1;
@@ -670,7 +685,7 @@
display.setFont(font5x7);
#else
display.setFont(fontC64);
- #endif
+ #endif
#if POK_ENABLE_SOUND > 0
sound.begin();
@@ -1042,9 +1057,6 @@
//draw a fancy menu
display.textWrap = false;
- //uint16_t fc,bc;
- //fc = display.color;
- //bc = display.bgcolor;
if( updated ) { // update screen?
#if POK_SIM
getFirstFile(ext);
@@ -1103,11 +1115,12 @@
display.setColor(1,0);
}
+
return 0;
}
char* Core::filemenu() {
- return filemenu("");
+ return filemenu((char*)"");
}
int8_t Core::menu(const char* const* items, uint8_t length) {
@@ -1345,6 +1358,10 @@
sound.prescaler = __avrmax(1, sound.prescaler);
}
+uint8_t Core::getFrameRate() {
+ return 1000 / timePerFrame;
+}
+
void Core::pickRandomSeed(){
initRandom();
}
--- a/POKITTO_CORE/PokittoCore.h Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_CORE/PokittoCore.h Sat Mar 23 20:03:34 2019 +0000
@@ -62,7 +62,6 @@
#include "PokittoFakeavr.h"
#define PALETTE_SIZE 256
-#undef PI
#define PI 3.141592741f
// For GB compatibility
@@ -226,6 +225,7 @@
static void keyboard(char* text, uint8_t length);
static void popup(const char* text, uint8_t duration);
static void setFrameRate(uint8_t fps);
+ static uint8_t getFrameRate();
static void pickRandomSeed();
static uint8_t getCpuLoad();
--- a/POKITTO_CORE/PokittoDisk.cpp Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_CORE/PokittoDisk.cpp Sat Mar 23 20:03:34 2019 +0000
@@ -56,14 +56,16 @@
return dot + 1;
}
-__attribute__((section(".SD_Code"))) void initSDGPIO() {
+//__attribute__((section(".SD_Code")))
+void initSDGPIO() {
LPC_GPIO_PORT->DIR[SD_MOSI_PORT] |= (1 << SD_MOSI_PIN );
LPC_GPIO_PORT->DIR[SD_MISO_PORT] |= (1 << SD_MISO_PIN );
LPC_GPIO_PORT->DIR[SD_SCK_PORT] |= (1 << SD_SCK_PIN );
LPC_GPIO_PORT->DIR[SD_CS_PORT] |= (1 << SD_CS_PIN );
}
-__attribute__((section(".SD_Code"))) int pokInitSD() {
+//__attribute__((section(".SD_Code")))
+int pokInitSD() {
initSDGPIO();
res = PFFS::disk_initialize();
//res = disk_initialize(0);
@@ -81,12 +83,12 @@
/** PUBLIC FUNCTIONS **/
-char* getFirstDirEntry() {
+char* getFirstDirEntry(char* path) {
res=0;
if (!diropened) {
pokInitSD();
}
- res = pf_opendir(&dir,"");
+ res = pf_opendir(&dir,path);
emptyFname();
res = pf_readdir(&dir,&fno); //returns 0 if everything is OK
if (res) return 0;
@@ -108,6 +110,10 @@
return 0;
}
+char* getFirstDirEntry() {
+ return getFirstDirEntry("");
+}
+
char* getNextDirEntry() {
if (!diropened) pokInitSD();
emptyFname();
@@ -162,12 +168,12 @@
return getNextFile("");
}
-char* getFirstFile(char* ext) {
+char* getFirstFile(char* ext, char* path) {
res=0;
if (!diropened) {
pokInitSD();
}
- res = pf_opendir(&dir,"");
+ res = pf_opendir(&dir,path);
emptyFname();
res = pf_readdir(&dir,&fno); //returns 0 if everything is OK
if (res) return 0;
@@ -184,6 +190,10 @@
return 0;
}
+char* getFirstFile(char* ext) {
+ return getFirstFile(ext, "");
+}
+
char* getFirstFile() {
return getFirstFile("");
}
--- a/POKITTO_CORE/PokittoDisk.h Sat Mar 23 19:22:35 2019 +0000 +++ b/POKITTO_CORE/PokittoDisk.h Sat Mar 23 20:03:34 2019 +0000 @@ -64,7 +64,7 @@ // CS ... #define CONNECT_CS P0_7 //p13 #define CLR_SD_CS LPC_GPIO_PORT->CLR[0] = (1 << 7) #define SET_SD_CS LPC_GPIO_PORT->SET[0] = (1 << 7) -#define GET_SD_CS LPC_GPIO_PORT->PIN[0] & (1 << 7) +#define GET_SD_CS ((LPC_GPIO_PORT->PIN[0]) & (1 << 7)) #else // simulated disk driver @@ -104,9 +104,11 @@ extern char* getCurrentFileName (); extern char* getNextFile (char*); extern char* getNextFile (); -extern char* getFirstFile(char*); +extern char* getFirstFile(char* ext); +extern char* getFirstFile(char* ext, char* path); extern char* getFirstFile(); extern char* getFirstDirEntry(); +extern char* getFirstDirEntry(char* path); extern char* getNextDirEntry(); extern int isThisFileOpen(char*); extern int fileOK();
--- a/POKITTO_CORE/PokittoGlobs.h Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_CORE/PokittoGlobs.h Sat Mar 23 20:03:34 2019 +0000
@@ -52,8 +52,6 @@
extern int random(int);
extern int random(int,int);
-#undef HIGH
-#undef LOW
#define HIGH 1
#define LOW 0
@@ -78,7 +76,11 @@
#if POK_STREAMING_MUSIC
#define SPEAKER 3
// #define BUFFER_SIZE 512 //5120 // was 256
+#if POK_HIGH_RAM == HIGH_RAM_MUSIC
+ extern unsigned char *buffers[];
+#else
extern unsigned char buffers[][BUFFER_SIZE];
+#endif
extern volatile int currentBuffer, oldBuffer;
extern volatile int bufindex, vol;
extern volatile unsigned char * currentPtr;
--- a/POKITTO_CORE/PokittoItoa.cpp Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_CORE/PokittoItoa.cpp Sat Mar 23 20:03:34 2019 +0000
@@ -38,6 +38,21 @@
#include <string.h>
#include <stdint.h>
+/* A utility function to reverse a string */
+void reverse(char str[], int length)
+{
+ int start = 0;
+ int end = length -1;
+ while (start < end)
+ {
+ char t = *(str+end);
+ *(str+end) = *(str+start);
+ *(str+start) = t;
+ //std::swap(*(str+start), *(str+end));
+ start++;
+ end--;
+ }
+}
void pokItoa(uint16_t value, char *str, int base)
{
@@ -134,8 +149,44 @@
pokItoa(value,str,base);
}
-void pokLtoa(long value, char *str, int base) {
- pokItoa(value,str,base);
+void pokLtoa(long num, char *str, int base) {
+ int i = 0;
+ bool isNegative = false;
+
+ /* Handle 0 explicitely, otherwise empty string is printed for 0 */
+ if (num == 0)
+ {
+ str[i++] = '0';
+ str[i] = '\0';
+ return;// str;
+ }
+
+ // In standard itoa(), negative numbers are handled only with
+ // base 10. Otherwise numbers are considered unsigned.
+ if (num < 0 && base == 10)
+ {
+ isNegative = true;
+ num = -num;
+ }
+
+ // Process individual digits
+ while (num != 0)
+ {
+ int rem = num % base;
+ str[i++] = (rem > 9)? (rem-10) + 'a' : rem + '0';
+ num = num/base;
+ }
+
+ // If number is negative, append '-'
+ if (isNegative)
+ str[i++] = '-';
+
+ str[i] = '\0'; // Append string terminator
+
+ // Reverse the string
+ reverse(str, i);
+
+ return;// str;
}
--- a/POKITTO_CORE/PokittoPalette.cpp Sat Mar 23 19:22:35 2019 +0000 +++ b/POKITTO_CORE/PokittoPalette.cpp Sat Mar 23 20:03:34 2019 +0000 @@ -46,7 +46,7 @@ #include "SimLCD.h" #endif -#ifndef PROJ_MODE13 +#if PROJ_SCREENMODE != 13 && PROJ_SCREENMODE != 64 && !defined(PROJ_MODE13) && !defined(PROJ_MODE64) #define PALSIZE 16 #else #define PALSIZE 256
--- a/POKITTO_CORE/PokittoSound.cpp Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_CORE/PokittoSound.cpp Sat Mar 23 20:03:34 2019 +0000
@@ -43,7 +43,7 @@
*
* License for Gamebuino-identical code:
*
- * (C) Copyright 2014 Aur�lien Rodot. All rights reserved.
+ * (C) Copyright 2014 Aurélien Rodot. All rights reserved.
*
* This file is part of the Gamebuino Library (http://gamebuino.com)
*
@@ -68,6 +68,11 @@
#ifndef POK_SIM
#include "HWSound.h"
+
+#ifdef PROJ_SDFS_STREAMING
+#include "SDFSDisk.h"
+#endif
+
#else
#include "SimSound.h"
#include "PokittoSimulator.h"
@@ -77,15 +82,22 @@
using namespace Pokitto;
+#ifdef PROJ_SND_DEBUG
+int __sx=0;
+#endif
+
/** discrete hardware volume control **/
uint8_t Pokitto::discrete_vol = 0;
-uint8_t const Pokitto::discrete_vol_levels[] = {0,32,64,96,128,160,192,224};
-uint8_t const Pokitto::discrete_vol_hw_levels[] = {0,27,64,96,36,117,127,127};
-uint8_t const Pokitto::discrete_vol_multipliers[] = {0,127,127,127,192,192,255,255};
+uint8_t const Pokitto::discrete_vol_levels[8] {0,32,64,96,128,160,192,224};
+uint8_t const Pokitto::discrete_vol_hw_levels[8] {0,27,64,96,36,117,127,127};
+uint8_t const Pokitto::discrete_vol_multipliers[8] {0,127,127,127,192,192,255,255};
Pokitto::Core _soundc;
+const uint8_t *Sound::sfxDataPtr = 0;
+const uint8_t *Sound::sfxEndPtr = 0;
+
uint8_t Sound::prescaler;
uint16_t Sound::globalVolume;
uint16_t Sound::volumeMax = VOLUME_HEADPHONE_MAX;
@@ -135,8 +147,10 @@
uint8_t Sound::chanVolumes[NUM_CHANNELS];
#if (POK_ENABLE_SOUND < 1)
+ #ifdef NUM_CHANNELS
#undef NUM_CHANNELS
#define NUM_CHANNELS 0
+ #endif // NUM_CHANNELS
#endif
#if(NUM_CHANNELS > 0)
@@ -609,6 +623,7 @@
// jonnehw noInterrupts();
_chanHalfPeriod[i] = pgm_read_byte(_halfPeriods + outputPitch[i]);
_chanOutput[i] = _chanOutputVolume[i] = outputVolume[i] * (globalVolume>>GLOBVOL_SHIFT) * chanVolumes[i] * stepVolume[i];
+ //_chanOutput[i] = _chanOutputVolume[i] = outputVolume[i] * (globalVolume) * chanVolumes[i] * stepVolume[i];
//Serial.println(outputVolume[i]);
// jonnehw interrupts();
}
@@ -752,6 +767,7 @@
output >>= 8;
dac_write((uint8_t)output); //direct hardware mixing baby !
soundbyte = output;
+
#endif //POK_ENABLE_SOUND
#else
/** SIMULATOR **/
@@ -763,6 +779,7 @@
#endif
soundbyte = output;//<<headPhoneLevel;
#endif // POK_SIM
+
#endif
}
@@ -803,12 +820,14 @@
if (volume<0) volume = 0;
//if (volume>volumeMax) volume = volumeMax;
globalVolume = volume;
- #if POK_ENABLE_SOUND > 0
+ //#if POK_ENABLE_SOUND > 0
discrete_vol = (volume>>5);
#ifndef POK_SIM
+ #if POK_ENABLE_SOUND > 0
setHWvolume(discrete_vol_hw_levels[discrete_vol]); //boost volume if headphonelevel
#endif
#endif
+ //#endif
#if POK_SHOW_VOLUME > 0
_soundc.volbar_visible = VOLUMEBAR_TIMEOUT;
#endif
@@ -845,7 +864,7 @@
void Sound::playTone(uint8_t os, int frq, uint8_t amp, uint8_t wav,uint8_t arpmode)
{
- if (wav>5) wav=0;
+ if (wav>MAX_WAVETYPES) wav=0;
if (arpmode>MAX_ARPMODE) arpmode=MAX_ARPMODE;
if (os==1) setOSC(&osc1,1,wav,1,0,0,frq,amp,0,0,0,0,0,0,arpmode,0,0);
else if (os==2) setOSC(&osc2,1,wav,1,0,0,frq,amp,0,0,0,0,0,0,arpmode,0,0);
@@ -893,9 +912,9 @@
if (currentPtr) {
pokPlayStream();
return 1;
- } else return 0; //no stream
+ }
#endif // POK_STREAMING_MUSIC
- return 0;
+ return 0; //no stream
}
void Sound::pauseMusicStream() {
@@ -907,12 +926,16 @@
int Sound::playMusicStream(char* filename, uint8_t options)
{
#if POK_STREAMING_MUSIC
+
uint8_t result;
result = pokInitSD();
if (!isThisFileOpen(filename)) {
fileClose(); // close any open files
result = fileOpen(filename,FILE_MODE_READONLY | FILE_MODE_BINARY);
- }
+ }else{
+ fileRewind();
+ result = 0;
+ }
if (result) {
currentPtr = 0; // mark that no stream is available
@@ -948,3 +971,13 @@
return 0;
}
+void Sound::loadSampleToOsc(uint8_t os, uint8_t* data, uint32_t datasize) {
+ OSC* o;
+ if (os==3) o = &osc3;
+ else if (os==2) o = &osc2;
+ else o = &osc1;
+ o->sample = data;
+ o->samplelength = datasize;
+ o->samplepos = 0;
+}
+
--- a/POKITTO_CORE/PokittoSound.h Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_CORE/PokittoSound.h Sat Mar 23 20:03:34 2019 +0000
@@ -104,6 +104,13 @@
static uint16_t volumeMax;
public:
+ static const uint8_t *sfxDataPtr;
+ static const uint8_t *sfxEndPtr;
+ static void playSFX( const uint8_t *sfx, uint32_t length ){
+ sfxDataPtr = sfx;
+ sfxEndPtr = sfx + length;
+ };
+
static void begin();
// Headphonemode
@@ -113,6 +120,9 @@
static void volumeUp();
static void volumeDown();
+ // Synth using samples support
+ static void loadSampleToOsc(uint8_t os, uint8_t* sampdata, uint32_t sampsize);
+
// Original functions
static void updateStream();
static void playTone(uint8_t os, int frq, uint8_t amp, uint8_t wav,uint8_t arpmode);
--- a/POKITTO_LIBS/Synth/Synth.cpp Sat Mar 23 19:22:35 2019 +0000 +++ b/POKITTO_LIBS/Synth/Synth.cpp Sat Mar 23 20:03:34 2019 +0000 @@ -36,17 +36,19 @@ #include "Pokitto.h" #include "Synth.h" +#include "stdint.h" +#include "My_settings.h" /** COMMON TO BOTH HW AND SIMULATED SOUND **/ -boolean playing=false; //external to share between player and synth -boolean track1on = true, track2on = true, track3on = true, tableRefresh = false; +bool playing=false; //external to share between player and synth +bool track1on = true, track2on = true, track3on = true, tableRefresh = false; uint8_t sequencepos=0, tempo = 120; long writeindex=0, readindex=0; uint16_t playerpos=0; -long per = 1000*60/tempo/4; // ms per minute was 1000*60 -uint16_t samplespertick = (uint16_t)per*57, notetick; // samplespertick is a calculated value based on song speed. notetick is a counter +uint16_t samplespertick = (float)((60.0f/(float)tempo)*POK_AUD_FREQ)/16; +uint16_t notetick=0; // samplespertick is a calculated value based on song speed. notetick is a counter long samplesperpattern=0; uint8_t tick=3; // loops between 3 channels. Tick 3 is used to calculate volume envelopes @@ -54,8 +56,8 @@ SONG song; OSC osc1,osc2,osc3; -OSC patch[15]; -BLOCK block[1]; //30 blocks maximum +OSC patch[MAXPATCHES]; +BLOCK block[MAXBLOCKS];
--- a/POKITTO_LIBS/Synth/Synth.h Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_LIBS/Synth/Synth.h Sat Mar 23 20:03:34 2019 +0000
@@ -36,15 +36,20 @@
}
*/
-#ifndef boolean
-typedef bool boolean;
-#endif
+#define OPT_ADSR 1
+#define OPT_LOOP 2
+#define OPT_ECHO 4
+#define OPT_OVERDRIVE 8
+#define OPT_NORMALIZE 0x10
+
+#define OVERDRIVE 4
//extern void fakeISR(); // was defined in Rboy_soundsim.h
typedef void (*waveFunction)(OSC*);
typedef void (*envFunction)(OSC*);
typedef void (*mixFunction)();
+typedef void (*streamsFunction)();
extern waveFunction Farr [];
extern envFunction Earr [];
@@ -67,10 +72,21 @@
#define ARPSTEPMAX 4 // was 5
#define PATTERNLENGTH 64
#define MAXPATTERNS 10
+
+#ifdef PROJ_SYNTH_MAXBLOCKS
+#define MAXBLOCKS PROJ_SYNTH_MAXBLOCKS
+#else
#define MAXBLOCKS 30 // 10 *3
+#endif
-#define VOLTICK 5
-#define ARPTICK 50 // 150 // was 200
+#ifdef PROJ_SYNTH_MAXPATCHES
+#define MAXPATCHES PROJ_SYNTH_MAXPATCHES
+#else
+#define MAXPATCHES 15
+#endif
+
+#define VOLTICK POK_AUD_FREQ/8820 //was 5
+#define ARPTICK POK_AUD_FREQ/441 // 150 // was 200
#define NUMWAVES 5
#define NUMENVELOPES 3
@@ -100,9 +116,10 @@
extern int openSongFromSD(char *);
extern void writeChunkToSD(uint8_t *);
extern void readChunkFromSD(uint8_t *);
-
+extern void registerStreamsCallback(streamsFunction);
+extern streamsFunction streamCallbackPtr;
-extern boolean playing, track1on, track2on, track3on, tableRefresh;
+extern bool playing, track1on, track2on, track3on, tableRefresh;
extern uint16_t playerpos;
extern uint16_t samplespertick, notetick;
extern long samplesperpattern;
@@ -116,6 +133,7 @@
extern BLOCK block[]; // array of blocks
#define MAX_ARPMODE 16
+#define MAX_WAVETYPES 6
extern int8_t arptable[][5];
@@ -129,7 +147,7 @@
extern uint16_t noiseval;
extern void setOSC(OSC*,byte, byte, byte, byte, byte,
- uint8_t, uint8_t,
+ uint8_t, uint16_t,
uint16_t, uint16_t, uint16_t, uint16_t,
int16_t, int16_t, uint8_t, uint8_t, uint8_t);
--- a/POKITTO_LIBS/Synth/Synth_helpers.cpp Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_LIBS/Synth/Synth_helpers.cpp Sat Mar 23 20:03:34 2019 +0000
@@ -639,97 +639,97 @@
/** NOTE TO TEXT TABLES **/
-const char note_0[] PROGMEM = "B-0"; // 0 - NOTE_B0
-const char note_1[] PROGMEM = "C-1"; // 1 - NOTE_C1
-const char note_2[] PROGMEM = "C#1"; // 2 - NOTE_CS1
-const char note_3[] PROGMEM = "D-1"; // 3 - NOTE_D1
-const char note_4[] PROGMEM = "D#1"; // 4 - NOTE_DS1
-const char note_5[] PROGMEM = "E-1"; // 5 - NOTE_E1
-const char note_6[] PROGMEM = "F-1"; // 6 - NOTE_F1
-const char note_7[] PROGMEM = "F#1"; // 7 - NOTE_FS1
-const char note_8[] PROGMEM = "G-1"; // 8 - NOTE_G1
-const char note_9[] PROGMEM = "G#1"; // 9 - NOTE_GS1
-const char note_10[] PROGMEM = "A-1"; // 10 - NOTE_A1
-const char note_11[] PROGMEM = "A#1"; // 11 - NOTE_AS1
-const char note_12[] PROGMEM = "B-1"; // 12 - NOTE_B1
-const char note_13[] PROGMEM = "C-2"; // 2 - NOTE_C2
-const char note_14[] PROGMEM = "C#2"; // 2 - NOTE_CS2
-const char note_15[] PROGMEM = "D-2"; // 3 - NOTE_D2
-const char note_16[] PROGMEM = "D#2"; // 4 - NOTE_DS2
-const char note_17[] PROGMEM = "E-2"; // 5 - NOTE_E2
-const char note_18[] PROGMEM = "F-2"; // 6 - NOTE_F2
-const char note_19[] PROGMEM = "F#2"; // 7 - NOTE_FS2
-const char note_20[] PROGMEM = "G-2"; // 8 - NOTE_G2
-const char note_21[] PROGMEM = "G#2"; // 9 - NOTE_GS2
-const char note_22[] PROGMEM = "A-2"; // 20 - NOTE_A2
-const char note_23[] PROGMEM = "A#2"; // 22 - NOTE_AS2
-const char note_24[] PROGMEM = "B-2"; // 22 - NOTE_B2
-const char note_25[] PROGMEM = "C-3"; // 3 - NOTE_C3
-const char note_26[] PROGMEM = "C#3"; // 3 - NOTE_CS3
-const char note_27[] PROGMEM = "D-3"; // 3 - NOTE_D3
-const char note_28[] PROGMEM = "D#3"; // 4 - NOTE_DS3
-const char note_29[] PROGMEM = "E-3"; // 5 - NOTE_E3
-const char note_30[] PROGMEM = "F-3"; // 6 - NOTE_F3
-const char note_31[] PROGMEM = "F#3"; // 7 - NOTE_FS3
-const char note_32[] PROGMEM = "G-3"; // 8 - NOTE_G3
-const char note_33[] PROGMEM = "G#3"; // 9 - NOTE_GS3
-const char note_34[] PROGMEM = "A-3"; // 30 - NOTE_A3
-const char note_35[] PROGMEM = "A#3"; // 33 - NOTE_AS3
-const char note_36[] PROGMEM = "B-3"; // 33 - NOTE_B3
-const char note_37[] PROGMEM = "C-4"; // 4 - NOTE_C4
-const char note_38[] PROGMEM = "C#4"; // 4 - NOTE_CS4
-const char note_39[] PROGMEM = "D-4"; // 3 - NOTE_D4
-const char note_40[] PROGMEM = "D#4"; // 4 - NOTE_DS4
-const char note_41[] PROGMEM = "E-4"; // 5 - NOTE_E4
-const char note_42[] PROGMEM = "F-4"; // 6 - NOTE_F4
-const char note_43[] PROGMEM = "F#4"; // 7 - NOTE_FS4
-const char note_44[] PROGMEM = "G-4"; // 8 - NOTE_G4
-const char note_45[] PROGMEM = "G#4"; // 9 - NOTE_GS4
-const char note_46[] PROGMEM = "A-4"; // 40 - NOTE_A4
-const char note_47[] PROGMEM = "A#4"; // 44 - NOTE_AS4
-const char note_48[] PROGMEM = "B-4"; // 44 - NOTE_B4
-const char note_49[] PROGMEM = "C-5"; // 5 - NOTE_C5
-const char note_50[] PROGMEM = "C#5"; // 5 - NOTE_CS5
-const char note_51[] PROGMEM = "D-5"; // 3 - NOTE_D5
-const char note_52[] PROGMEM = "D#5"; // 4 - NOTE_DS5
-const char note_53[] PROGMEM = "E-5"; // 5 - NOTE_E5
-const char note_54[] PROGMEM = "F-5"; // 6 - NOTE_F5
-const char note_55[] PROGMEM = "F#5"; // 7 - NOTE_FS5
-const char note_56[] PROGMEM = "G-5"; // 8 - NOTE_G5
-const char note_57[] PROGMEM = "G#5"; // 9 - NOTE_GS5
-const char note_58[] PROGMEM = "A-5"; // 50 - NOTE_A5
-const char note_59[] PROGMEM = "A#5"; // 55 - NOTE_AS5
-const char note_60[] PROGMEM = "B-5"; // 55 - NOTE_B5
-const char note_61[] PROGMEM = "C-6"; // 6 - NOTE_C6
-const char note_62[] PROGMEM = "C#6"; // 6 - NOTE_CS6
-const char note_63[] PROGMEM = "D-6"; // 3 - NOTE_D6
-const char note_64[] PROGMEM = "D#6"; // 4 - NOTE_DS6
-const char note_65[] PROGMEM = "E-6"; // 5 - NOTE_E6
-const char note_66[] PROGMEM = "F-6"; // 6 - NOTE_F6
-const char note_67[] PROGMEM = "F#6"; // 7 - NOTE_FS6
-const char note_68[] PROGMEM = "G-6"; // 8 - NOTE_G6
-const char note_69[] PROGMEM = "G#6"; // 9 - NOTE_GS6
-const char note_70[] PROGMEM = "A-6"; // 60 - NOTE_A6
-const char note_71[] PROGMEM = "A#6"; // 66 - NOTE_AS6
-const char note_72[] PROGMEM = "B-6"; // 66 - NOTE_B6
-const char note_73[] PROGMEM = "C-7"; // 7 - NOTE_C7
-const char note_74[] PROGMEM = "C#7"; // 7 - NOTE_CS7
-const char note_75[] PROGMEM = "D-7"; // 3 - NOTE_D7
-const char note_76[] PROGMEM = "D#7"; // 4 - NOTE_DS7
-const char note_77[] PROGMEM = "E-7"; // 5 - NOTE_E7
-const char note_78[] PROGMEM = "F-7"; // 6 - NOTE_F7
-const char note_79[] PROGMEM = "F#7"; // 7 - NOTE_FS7
-const char note_80[] PROGMEM = "G-7"; // 8 - NOTE_G7
-const char note_81[] PROGMEM = "G#7"; // 9 - NOTE_GS7
-const char note_82[] PROGMEM = "A-7"; // 70 - NOTE_A7
-const char note_83[] PROGMEM = "A#7"; // 77 - NOTE_AS7
-const char note_84[] PROGMEM = "B-7"; // 77 - NOTE_B7
-const char note_85[] PROGMEM = "C-8"; // 8 - NOTE_C8
-const char note_86[] PROGMEM = "C#8"; // 8 - NOTE_CS8
-const char note_87[] PROGMEM = "D-8"; // 3 - NOTE_D8
-const char note_88[] PROGMEM = "D#8"; // 4 - NOTE_DS8
+const char note_0[] = "B-0"; // 0 - NOTE_B0
+const char note_1[] = "C-1"; // 1 - NOTE_C1
+const char note_2[] = "C#1"; // 2 - NOTE_CS1
+const char note_3[] = "D-1"; // 3 - NOTE_D1
+const char note_4[] = "D#1"; // 4 - NOTE_DS1
+const char note_5[] = "E-1"; // 5 - NOTE_E1
+const char note_6[] = "F-1"; // 6 - NOTE_F1
+const char note_7[] = "F#1"; // 7 - NOTE_FS1
+const char note_8[] = "G-1"; // 8 - NOTE_G1
+const char note_9[] = "G#1"; // 9 - NOTE_GS1
+const char note_10[] = "A-1"; // 10 - NOTE_A1
+const char note_11[] = "A#1"; // 11 - NOTE_AS1
+const char note_12[] = "B-1"; // 12 - NOTE_B1
+const char note_13[] = "C-2"; // 2 - NOTE_C2
+const char note_14[] = "C#2"; // 2 - NOTE_CS2
+const char note_15[] = "D-2"; // 3 - NOTE_D2
+const char note_16[] = "D#2"; // 4 - NOTE_DS2
+const char note_17[] = "E-2"; // 5 - NOTE_E2
+const char note_18[] = "F-2"; // 6 - NOTE_F2
+const char note_19[] = "F#2"; // 7 - NOTE_FS2
+const char note_20[] = "G-2"; // 8 - NOTE_G2
+const char note_21[] = "G#2"; // 9 - NOTE_GS2
+const char note_22[] = "A-2"; // 20 - NOTE_A2
+const char note_23[] = "A#2"; // 22 - NOTE_AS2
+const char note_24[] = "B-2"; // 22 - NOTE_B2
+const char note_25[] = "C-3"; // 3 - NOTE_C3
+const char note_26[] = "C#3"; // 3 - NOTE_CS3
+const char note_27[] = "D-3"; // 3 - NOTE_D3
+const char note_28[] = "D#3"; // 4 - NOTE_DS3
+const char note_29[] = "E-3"; // 5 - NOTE_E3
+const char note_30[] = "F-3"; // 6 - NOTE_F3
+const char note_31[] = "F#3"; // 7 - NOTE_FS3
+const char note_32[] = "G-3"; // 8 - NOTE_G3
+const char note_33[] = "G#3"; // 9 - NOTE_GS3
+const char note_34[] = "A-3"; // 30 - NOTE_A3
+const char note_35[] = "A#3"; // 33 - NOTE_AS3
+const char note_36[] = "B-3"; // 33 - NOTE_B3
+const char note_37[] = "C-4"; // 4 - NOTE_C4
+const char note_38[] = "C#4"; // 4 - NOTE_CS4
+const char note_39[] = "D-4"; // 3 - NOTE_D4
+const char note_40[] = "D#4"; // 4 - NOTE_DS4
+const char note_41[] = "E-4"; // 5 - NOTE_E4
+const char note_42[] = "F-4"; // 6 - NOTE_F4
+const char note_43[] = "F#4"; // 7 - NOTE_FS4
+const char note_44[] = "G-4"; // 8 - NOTE_G4
+const char note_45[] = "G#4"; // 9 - NOTE_GS4
+const char note_46[] = "A-4"; // 40 - NOTE_A4
+const char note_47[] = "A#4"; // 44 - NOTE_AS4
+const char note_48[] = "B-4"; // 44 - NOTE_B4
+const char note_49[] = "C-5"; // 5 - NOTE_C5
+const char note_50[] = "C#5"; // 5 - NOTE_CS5
+const char note_51[] = "D-5"; // 3 - NOTE_D5
+const char note_52[] = "D#5"; // 4 - NOTE_DS5
+const char note_53[] = "E-5"; // 5 - NOTE_E5
+const char note_54[] = "F-5"; // 6 - NOTE_F5
+const char note_55[] = "F#5"; // 7 - NOTE_FS5
+const char note_56[] = "G-5"; // 8 - NOTE_G5
+const char note_57[] = "G#5"; // 9 - NOTE_GS5
+const char note_58[] = "A-5"; // 50 - NOTE_A5
+const char note_59[] = "A#5"; // 55 - NOTE_AS5
+const char note_60[] = "B-5"; // 55 - NOTE_B5
+const char note_61[] = "C-6"; // 6 - NOTE_C6
+const char note_62[] = "C#6"; // 6 - NOTE_CS6
+const char note_63[] = "D-6"; // 3 - NOTE_D6
+const char note_64[] = "D#6"; // 4 - NOTE_DS6
+const char note_65[] = "E-6"; // 5 - NOTE_E6
+const char note_66[] = "F-6"; // 6 - NOTE_F6
+const char note_67[] = "F#6"; // 7 - NOTE_FS6
+const char note_68[] = "G-6"; // 8 - NOTE_G6
+const char note_69[] = "G#6"; // 9 - NOTE_GS6
+const char note_70[] = "A-6"; // 60 - NOTE_A6
+const char note_71[] = "A#6"; // 66 - NOTE_AS6
+const char note_72[] = "B-6"; // 66 - NOTE_B6
+const char note_73[] = "C-7"; // 7 - NOTE_C7
+const char note_74[] = "C#7"; // 7 - NOTE_CS7
+const char note_75[] = "D-7"; // 3 - NOTE_D7
+const char note_76[] = "D#7"; // 4 - NOTE_DS7
+const char note_77[] = "E-7"; // 5 - NOTE_E7
+const char note_78[] = "F-7"; // 6 - NOTE_F7
+const char note_79[] = "F#7"; // 7 - NOTE_FS7
+const char note_80[] = "G-7"; // 8 - NOTE_G7
+const char note_81[] = "G#7"; // 9 - NOTE_GS7
+const char note_82[] = "A-7"; // 70 - NOTE_A7
+const char note_83[] = "A#7"; // 77 - NOTE_AS7
+const char note_84[] = "B-7"; // 77 - NOTE_B7
+const char note_85[] = "C-8"; // 8 - NOTE_C8
+const char note_86[] = "C#8"; // 8 - NOTE_CS8
+const char note_87[] = "D-8"; // 3 - NOTE_D8
+const char note_88[] = "D#8"; // 4 - NOTE_DS8
-const char* note_table[] PROGMEM = {
+const char* note_table[] = {
note_0,
note_1,
note_2,
--- a/POKITTO_LIBS/Synth/Synth_mixfuncs.cpp Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_LIBS/Synth/Synth_mixfuncs.cpp Sat Mar 23 20:03:34 2019 +0000
@@ -48,12 +48,12 @@
// Track 1
if (osc1.on) {
Farr[osc1.wave](&osc1);
- #if PROJ_ARDUBOY > 0
+ //#if PROJ_ARDUBOY > 0
if (osc1.duration) {
/**this is special for osc1 and is only used to emulate arduino Tone(); */
osc1.duration--;
} else osc1.on = 0;
- #endif
+ //#endif
#ifdef POK_SIM
soundbyte = (((osc1.output>>8) * (osc1.adsrvol >>8 )) >> 8) >> osc1.echodiv; // To output, shift back to 8-bit
@@ -76,6 +76,10 @@
// Track 2
if (osc2.on) {
Farr[osc2.wave](&osc2);
+ if (osc2.duration) {
+ osc2.duration--;
+ } else osc2.on = 0;
+
#ifdef POK_SIM
soundbyte = (((osc2.output>>8) * (osc2.adsrvol >>8 )) >> 8) >> osc2.echodiv;
if (osc2.overdrive) soundbyte *= OVERDRIVE;
@@ -97,6 +101,9 @@
// Track 3
if (osc3.on) {
Farr[osc3.wave](&osc3);
+ if (osc3.duration) {
+ osc3.duration--;
+ } else osc3.on = 0;
#ifdef POK_SIM
soundbyte = (((osc3.output>>8) * (osc3.adsrvol >>8 )) >> 8) >> osc3.echodiv;
if (osc3.overdrive) soundbyte *= OVERDRIVE;
@@ -116,7 +123,11 @@
void updateEnvelopes(){
//calculate volume envelopes, I do this to save cpu power
+ #if POK_ALT_MIXING > 0
if (arptick) --arptick;
+ #else
+ if (arptick) --arptick;
+ #endif
else {
if (osc1.arpmode && osc1.on) {
osc1.cinc = cincs[osc1.tonic+arptable[osc1.arpmode][osc1.arpstep]];
@@ -139,11 +150,25 @@
}
+ #if POK_ALT_MIXING > 0
if (voltick) --voltick;
+ #else
+ if (voltick) --voltick;
+ #endif
else {
bendtick = !bendtick;
if (osc1.on) Earr[osc1.adsrphase](&osc1);
- if (bendtick) osc1.pitchbend += osc1.bendrate; //slow bend to every second beat
+ if (bendtick) {
+ osc1.pitchbend += osc1.bendrate; //slow bend to every second beat
+ /*if (osc1.wave == 6 && osc1.bendrate) {
+ if (osc1.samplebendtick > osc1.samplebendcount) {
+ if (osc1.bendrate>0) osc1.samplestep++;
+ else if (osc1.bendrate<0) osc1.samplestep--;
+ osc1.samplebendtick=0;
+ } else osc1.samplebendtick++;
+
+ }*/
+ }
if (osc1.bendrate > 0 && osc1.pitchbend > osc1.maxbend) {
osc1.pitchbend = osc1.maxbend;
osc1.bendrate = 0; // STOP BENDING !
--- a/POKITTO_LIBS/Synth/Synth_osc.h Sat Mar 23 19:22:35 2019 +0000 +++ b/POKITTO_LIBS/Synth/Synth_osc.h Sat Mar 23 20:03:34 2019 +0000 @@ -49,9 +49,9 @@ uint16_t sustain; // Attack change uint16_t release; // Attack change - int16_t pitchbend; // bends cycle counter (more is higher pitch) - int16_t maxbend; // maximum bend before stopping - int16_t bendrate; // how much to bend by every cycle + int32_t pitchbend; // bends cycle counter (more is higher pitch) + int32_t maxbend; // maximum bend before stopping + int32_t bendrate; // how much to bend by every cycle uint8_t vibrate; uint8_t arpmode; @@ -61,6 +61,14 @@ uint8_t kick; uint32_t duration; + + uint32_t samplepos; + uint32_t samplestep; + uint32_t samplelength; + uint8_t* sample; + //uint32_t samplebendcount; + //uint32_t samplebendtick; + };
--- a/POKITTO_LIBS/Synth/Synth_oscfuncs.cpp Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_LIBS/Synth/Synth_oscfuncs.cpp Sat Mar 23 20:03:34 2019 +0000
@@ -39,11 +39,12 @@
/** OSCILLATOR FUNCTIONS **/
void setOSC(OSC* o,byte on=1, byte wave=1, byte loop=0, byte echo=0, byte adsr=0,
- uint8_t notenumber=25, uint8_t volume=127,
+ uint8_t notenumber=25, uint16_t volume=127,
uint16_t attack=0, uint16_t decay=0, uint16_t sustain=0, uint16_t release=0,
int16_t maxbend=0, int16_t bendrate=0, uint8_t arpmode = 0, uint8_t overdrive=0, uint8_t kick=0){
//Serial.println("SetOsc "); osc1
o->on = on;
+ o->duration = -1; //max this out for the time being
o->overdrive = overdrive;
o->kick = kick;
o->wave = wave;
@@ -66,12 +67,13 @@
o->tonic = notenumber; // save tonic for arpeggio use
if (wave == 2) o->cinc >>= 1; // correct pitch for saw wave
if (wave == 4) o->cinc <<= 1; // enable higher pitch for pure noise
+ if (wave == 6) o->samplestep = (o->cinc/(cincs[37]>>8));
o->vol = volume << 8;//volume;
if (adsr) {
o->attack = attack;
o->decay = decay;
- o->sustain = sustain;
+ o->sustain = sustain<<8; //sustain needs to be multiplied by 256 also
o->release = release;
o->adsrphase = 1;
if (!o->attack) o->adsrvol = o->vol; // start directly, no attack ramp
@@ -85,10 +87,15 @@
o->adsrvol = o->vol; // will stay same all the time
}
+ o->pitchbend = 0; //this has to be zeroed always!
if (bendrate != 0) {
- o->bendrate = bendrate; // test value
- o->pitchbend = 0;
- o->maxbend = maxbend;
+ o->bendrate = (int32_t)bendrate*(o->cinc/10000); // test value
+ o->maxbend = (int32_t)maxbend*(o->cinc/100);
+ //o->samplebendcount = o->maxbend>>24;
+ //o->samplebendtick = 0;
+ } else {
+ o->bendrate = 0;
+ o->maxbend = 0;
}
}
--- a/POKITTO_LIBS/Synth/Synth_songfuncs.cpp Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_LIBS/Synth/Synth_songfuncs.cpp Sat Mar 23 20:03:34 2019 +0000
@@ -36,6 +36,9 @@
#include "PokittoDisk.h"
#include "Synth.h"
+#ifdef TRACKER_EXAMPLE
+#include "Tracker.h"
+#endif // TRACKER
#ifdef POK_SIM
#include "FileIO.h"
#endif
@@ -46,9 +49,10 @@
uint8_t chunk[2][CHUNKSIZE]; // 8 rows, 3 channels (columns), 2 bytes per entry
uint8_t cc = 0;
+streamsFunction streamCallbackPtr;
#if POK_ENABLE_SOUND > 0
-#if POK_ENABLE_SD > 0
+
void updatePlaybackSD(uint8_t row) {
// samplespertick determines how long the oscillators are active before they are recalculated (i.e. the next tick
uint8_t i=0;
@@ -157,7 +161,12 @@
}
}
playerpos = 0;
+ #ifdef TRACKER_EXAMPLE
+ tracker.initStreams();
+ #else
initStreams(sequencepos);
+ #endif // TRACKER_EXAMPLE
+ //(*streamCallbackPtr)();
tableRefresh=true;
}
notetick =0;
@@ -222,6 +231,8 @@
sequencepos = 0;
}
+#if POK_ENABLE_SD > 0
+
int openSongFromSD(char* buffer) {
if (!isThisFileOpen(buffer)) {
fileClose(); // close any open files
@@ -241,7 +252,13 @@
fileReadBytes(buffer, CHUNKSIZE);
}
}
-#endif
+
+#endif // POK_ENABLE_SD
+
+void registerStreamsCallback(streamsFunction ptr) {
+ streamCallbackPtr = ptr;
+}
+
#endif // POK_ENABLE_SOUND
--- a/POKITTO_LIBS/Synth/Synth_wavefuncs.cpp Sat Mar 23 19:22:35 2019 +0000
+++ b/POKITTO_LIBS/Synth/Synth_wavefuncs.cpp Sat Mar 23 20:03:34 2019 +0000
@@ -42,7 +42,7 @@
void noADSR(OSC* o); void attackFunc(OSC* o); void decayFunc(OSC* o); void releaseFunc(OSC* o);
void mix1(); void mix2(); void mix3(); void updateEnvelopes();
-waveFunction Farr [] = {waveoff, sqwave, sawwave, triwave, noise, tonenoise};
+waveFunction Farr [] = {waveoff, sqwave, sawwave, triwave, noise, tonenoise, sample};
envFunction Earr [] = {noADSR, attackFunc, decayFunc, releaseFunc};
mixFunction Marr [] = {updateEnvelopes,mix3,mix2,mix1}; // counts down
mixFunction HWMarr [] = {updateEnvelopes,mix3,mix2,mix1}; // counts down
@@ -97,14 +97,15 @@
}
void sample(OSC* o) {
-
- /*if (o->samplepos > o->samplelength ) o->samplepos = 0;
-
- if (o->count > o->wcycle) {
- o->count=0;
- if (o->output) o->output = 0;
- //else o->output = o->output=pgm_read_byte((uint32_t)(sfxBike) + o->inccount);
- }*/
+ if (sample==NULL) o->output = 0;
+ else {
+ o->samplepos+=o->samplestep;
+ if ((o->samplepos>>8) > o->samplelength ) {
+ o->samplepos = 0;
+ if (o->loop == 0) o->duration=0;
+ }
+ o->output = *(o->sample + (o->samplepos>>8))<<8;
+ }
}
--- a/Pokitto_settings.h Sat Mar 23 19:22:35 2019 +0000
+++ b/Pokitto_settings.h Sat Mar 23 20:03:34 2019 +0000
@@ -38,7 +38,7 @@
#ifndef POKITTO_SETTINGS_H
#define POKITTO_SETTINGS_H
-#include "../My_settings.h"
+#include "My_settings.h"
#ifdef PROJ_BOARDREV
#define POK_BOARDREV PROJ_BOARDREV // which revision of Pokitto board
@@ -76,6 +76,7 @@
#endif
#else
#define POK_GBSOUND PROJ_GBSOUND
+ //#define NUM_CHANNELS 2
#endif
@@ -91,6 +92,15 @@
#define POK_ENABLE_SYNTH PROJ_ENABLE_SYNTH
#endif // PROJ_ENABLE_SYNTH
+#define HIGH_RAM_OFF 0 // SRAM1/SRAM2 are at the default setting
+#define HIGH_RAM_ON 1 // SRAM1/SRAM2 are enabled and free for use
+#define HIGH_RAM_MUSIC 2 // SRAM1/SRAM2 are enabled and used by music
+
+#ifndef PROJ_HIGH_RAM
+#define POK_HIGH_RAM HIGH_RAM_OFF
+#else
+#define POK_HIGH_RAM PROJ_HIGH_RAM
+#endif
/** CONSOLE **/
#define POK_USE_CONSOLE 0 //if debugging console is available or not
@@ -209,8 +219,6 @@
#define BUFSIZE_HI_4 9680
#define MODE_FAST_16COLOR 2 //Size: 4840
#define BUFSIZE_FAST_16 4840
-#define MODE_HI_16COLOR 3
-#define BUFSIZE_HI_16 19360
#define MODE_GAMEBUINO_16COLOR 4 //Size: 2016
#define BUFSIZE_GAMEBUINO_16 2016
#define MODE_ARDUBOY_16COLOR 5 //Size: 4096
@@ -229,8 +237,14 @@
#define BUFSIZE_MODE_12 4176 // 72 x 58
#define MODE13 13
#define BUFSIZE_MODE13 9680 // 110*88
+#define MIXMODE 32
+#define BUFSIZE_MIXMODE 9680 // 110*88
+#define MODE64 64
+#define BUFSIZE_MODE64 19360 // 110*176
#define MODE14 14
#define BUFSIZE_MODE14 14520
+#define MODE15 15
+#define BUFSIZE_MODE15 19360
// Tiled modes
#define MODE_TILED_1BIT 1001
#define MODE_TILED_8BIT 1002
@@ -279,7 +293,7 @@
#endif
#endif // POK_TILEDMODE
-#if PROJ_MODE13 > 0
+#if PROJ_MODE13 > 0 || PROJ_SCREENMODE == 13
#undef POK_SCREENMODE //get rid of warnings
#undef POK_COLORDEPTH
#undef POK_FPS
@@ -289,7 +303,28 @@
#define POK_FPS 30
#endif
-#if PROJ_MODE14 > 0
+#if PROJ_MIXMODE > 0
+ #undef POK_SCREENMODE //get rid of warnings
+ #undef POK_COLORDEPTH
+ #undef POK_FPS
+ #define POK_SCREENMODE MIXMODE
+ #define POK_COLORDEPTH 8
+ #define POK_STRETCH 0
+ #define POK_FPS 30
+#endif
+
+
+#if PROJ_MODE64 > 0 || PROJ_SCREENMODE == 64
+ #undef POK_SCREENMODE //get rid of warnings
+ #undef POK_COLORDEPTH
+ #undef POK_FPS
+ #define POK_SCREENMODE MODE64
+ #define POK_COLORDEPTH 8
+ #define POK_STRETCH 0
+ #define POK_FPS 30
+#endif
+
+#if PROJ_MODE14 > 0 || PROJ_SCREENMODE == 14
#undef POK_SCREENMODE //get rid of warnings
#undef POK_COLORDEPTH
#undef POK_FPS
@@ -298,7 +333,7 @@
#define POK_STRETCH 0
#define POK_FPS 30
#endif
-#if PROJ_MODE15 > 0
+#if PROJ_MODE15 > 0 || PROJ_SCREENMODE == 15
#undef POK_SCREENMODE //get rid of warnings
#undef POK_COLORDEPTH
#undef POK_FPS
@@ -306,6 +341,7 @@
#define POK_COLORDEPTH 4
#define POK_STRETCH 0
#define POK_FPS 30
+ #define POK_BITFRAME 4840
#endif
/* DEFINE SCREENMODE AS THE MAXIMUM SCREEN SIZE NEEDED BY YOUR APP ... SEE SIZES LISTED ABOVE */
@@ -325,13 +361,8 @@
#define LCDWIDTH POK_LCD_W
#define LCDHEIGHT POK_LCD_H
#define POK_BITFRAME 4840
-#elif POK_SCREENMODE == MODE_HI_16COLOR
- #define POK_SCREENBUFFERSIZE POK_LCD_W*POK_LCD_H/2
- #define LCDWIDTH 220
- #define LCDHEIGHT 176
- #define POK_BITFRAME 4840
#elif POK_SCREENMODE == MODE_HI_4COLOR || POK_SCREENMODE == MODE_HI_GRAYSCALE
- #define POK_SCREENBUFFERSIZE POK_LCD_W*POK_LCD_H*POK_COLORDEPTH/4
+ #define POK_SCREENBUFFERSIZE (POK_LCD_W*POK_LCD_H*POK_COLORDEPTH/4)
#define LCDWIDTH POK_LCD_W
#define LCDHEIGHT POK_LCD_H
#define POK_BITFRAME 4840
@@ -374,6 +405,16 @@
#define LCDWIDTH 110
#define LCDHEIGHT 88
#define POK_BITFRAME 110*88
+#elif POK_SCREENMODE == MIXMODE
+ #define POK_SCREENBUFFERSIZE 110*88
+ #define LCDWIDTH 110
+ #define LCDHEIGHT 88
+ #define POK_BITFRAME 110*88
+#elif POK_SCREENMODE == MODE64
+ #define POK_SCREENBUFFERSIZE 110*176
+ #define LCDWIDTH 110
+ #define LCDHEIGHT 176
+ #define POK_BITFRAME 110*176
#elif POK_SCREENMODE == MODE14
#define POK_SCREENBUFFERSIZE 14520
#define LCDWIDTH 220
@@ -401,9 +442,16 @@
#define POK_FRAMEDURATION 1000/POK_FPS
/** SCROLL TEXT VS. WRAP AROUND WHEN PRINTING **/
+#if PROJ_NO_AUTO_SCROLL
+#define SCROLL_TEXT 0
+#else
#define SCROLL_TEXT 1
+#endif
/** AUDIO **/
+
+#define POK_ALT_MIXING 1 // NEW! alternative more accurate mixing, uses more CPU
+
#define POK_AUD_PIN P2_19
#define POK_AUD_PWM_US 15 //31 //Default value 31
#ifndef PROJ_AUD_FREQ
@@ -481,6 +529,14 @@
#define EESETTINGS_RTCALARMMODE 4011 // 0xFAB RTC alarm mode (0=disabled, 1=enabled, 3 = enabled with sound)
#define EESETTINGS_RESERVED 4012 // 0xFAC 4bytes reserved (additional sleep configuration)
#define EESETTINGS_WAKEUPTIME 4016 // 0xFB0 Wake-up time as 32bit value for 1Hz RTC clock
+#define EESETTINGS_SKIPINTRO 4020 // 0xFB4 Show Logo (0-Yes, 1-No, 2-Yes then switch to 0, 3-No, then switch to 1)
+
+/** USB SERIAL PORT **/
+
+#ifndef PROJ_VENDOR_ID
+#define POK_VENDOR_ID 0x04D8
+#define POK_PRODUCT_ID 0x000A
+#endif
#endif // POKITTO_SETTINGS_H