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

Committer:
Pokitto
Date:
Fri Dec 29 05:17:38 2017 +0000
Revision:
24:9561281d0378
Child:
28:958b71c4b92a
PokittoLib synced with Github and all Spianl & Hanski contributions so far

Who changed what in which revision?

UserRevisionLine numberNew contents of line
Pokitto 24:9561281d0378 1 /**************************************************************************/
Pokitto 24:9561281d0378 2 /*!
Pokitto 24:9561281d0378 3 @file PokittoCore.cpp
Pokitto 24:9561281d0378 4 @author Jonne Valola
Pokitto 24:9561281d0378 5
Pokitto 24:9561281d0378 6 @section LICENSE
Pokitto 24:9561281d0378 7
Pokitto 24:9561281d0378 8 Software License Agreement (BSD License)
Pokitto 24:9561281d0378 9
Pokitto 24:9561281d0378 10 Copyright (c) 2016, Jonne Valola
Pokitto 24:9561281d0378 11 All rights reserved.
Pokitto 24:9561281d0378 12
Pokitto 24:9561281d0378 13 Redistribution and use in source and binary forms, with or without
Pokitto 24:9561281d0378 14 modification, are permitted provided that the following conditions are met:
Pokitto 24:9561281d0378 15 1. Redistributions of source code must retain the above copyright
Pokitto 24:9561281d0378 16 notice, this list of conditions and the following disclaimer.
Pokitto 24:9561281d0378 17 2. Redistributions in binary form must reproduce the above copyright
Pokitto 24:9561281d0378 18 notice, this list of conditions and the following disclaimer in the
Pokitto 24:9561281d0378 19 documentation and/or other materials provided with the distribution.
Pokitto 24:9561281d0378 20 3. Neither the name of the copyright holders nor the
Pokitto 24:9561281d0378 21 names of its contributors may be used to endorse or promote products
Pokitto 24:9561281d0378 22 derived from this software without specific prior written permission.
Pokitto 24:9561281d0378 23
Pokitto 24:9561281d0378 24 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ''AS IS'' AND ANY
Pokitto 24:9561281d0378 25 EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
Pokitto 24:9561281d0378 26 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
Pokitto 24:9561281d0378 27 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
Pokitto 24:9561281d0378 28 DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
Pokitto 24:9561281d0378 29 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
Pokitto 24:9561281d0378 30 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
Pokitto 24:9561281d0378 31 ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
Pokitto 24:9561281d0378 32 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
Pokitto 24:9561281d0378 33 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
Pokitto 24:9561281d0378 34 */
Pokitto 24:9561281d0378 35 /**************************************************************************/
Pokitto 24:9561281d0378 36
Pokitto 24:9561281d0378 37 #include "PokittoCore.h"
Pokitto 24:9561281d0378 38 #include "Pokitto_settings.h"
Pokitto 24:9561281d0378 39 #include "PokittoConsole.h"
Pokitto 24:9561281d0378 40 #include "PokittoFonts.h"
Pokitto 24:9561281d0378 41 #include "PokittoTimer.h"
Pokitto 24:9561281d0378 42 #include "PokittoLogos.h"
Pokitto 24:9561281d0378 43 #include <stdlib.h>
Pokitto 24:9561281d0378 44 #ifndef DISABLEAVRMIN
Pokitto 24:9561281d0378 45 #define max(a,b) ((a)>(b)?(a):(b))
Pokitto 24:9561281d0378 46 #endif // DISABLEAVRMIN
Pokitto 24:9561281d0378 47
Pokitto 24:9561281d0378 48 char selectedfile[25];
Pokitto 24:9561281d0378 49
Pokitto 24:9561281d0378 50 //#define F
Pokitto 24:9561281d0378 51 #ifdef __ARMCC_VERSION
Pokitto 24:9561281d0378 52 typedef void (*func_t)(void);
Pokitto 24:9561281d0378 53 #endif
Pokitto 24:9561281d0378 54
Pokitto 24:9561281d0378 55 #ifndef POK_SIM
Pokitto 24:9561281d0378 56 #include "iap.h"
Pokitto 24:9561281d0378 57 /** start the user application
Pokitto 24:9561281d0378 58 * https://community.nxp.com/thread/417695
Pokitto 24:9561281d0378 59 *
Pokitto 24:9561281d0378 60 */
Pokitto 24:9561281d0378 61 void start_application(unsigned long app_link_location){
Pokitto 24:9561281d0378 62 //asm(" ldr sp, [r0,#0]");
Pokitto 24:9561281d0378 63 //asm(" ldr pc, [r0,#4]");
Pokitto 24:9561281d0378 64 //This code is not valid for the Cortex-m0+ instruction set.
Pokitto 24:9561281d0378 65 // The equivalent for this (as used by the KL26) is
Pokitto 24:9561281d0378 66 __disable_irq();// Start by disabling interrupts, before changing interrupt vectors
Pokitto 24:9561281d0378 67
Pokitto 24:9561281d0378 68 // delete buttons
Pokitto 24:9561281d0378 69 //pokDeleteButtons();
Pokitto 24:9561281d0378 70
Pokitto 24:9561281d0378 71 // completely kill button interrupts in preparation for reset
Pokitto 24:9561281d0378 72 LPC_PINT->IENR = 0;
Pokitto 24:9561281d0378 73 LPC_PINT->IENF = 0;
Pokitto 24:9561281d0378 74
Pokitto 24:9561281d0378 75 SysTick->CTRL = SysTick_CTRL_CLKSOURCE_Msk & ~(SysTick_CTRL_ENABLE_Msk); //disable systick
Pokitto 24:9561281d0378 76 LPC_SYSCON->PDRUNCFG |= (1 << 10); /* Power-down USB PHY */
Pokitto 24:9561281d0378 77 LPC_SYSCON->PDRUNCFG |= (1 << 8); /* Power-down USB PLL */
Pokitto 24:9561281d0378 78
Pokitto 24:9561281d0378 79 // reset clock source to IRC
Pokitto 24:9561281d0378 80 LPC_SYSCON->MAINCLKUEN = 0x01; /* Update MCLK Clock Source */
Pokitto 24:9561281d0378 81 LPC_SYSCON->MAINCLKUEN = 0x00; /* Toggle Update Register */
Pokitto 24:9561281d0378 82 while (LPC_SYSCON->MAINCLKUEN & 0x01); /* Wait Until Updated */
Pokitto 24:9561281d0378 83 // switch clock selection to IRC
Pokitto 24:9561281d0378 84 LPC_SYSCON->MAINCLKSEL = 0; /* Select Clock Source */
Pokitto 24:9561281d0378 85 LPC_SYSCON->MAINCLKUEN = 0x01; /* Update MCLK Clock Source */
Pokitto 24:9561281d0378 86 LPC_SYSCON->MAINCLKUEN = 0x00; /* Toggle Update Register */
Pokitto 24:9561281d0378 87 while (LPC_SYSCON->MAINCLKUEN & 0x01); /* Wait Until Updated */
Pokitto 24:9561281d0378 88 //disable PLL clock output
Pokitto 24:9561281d0378 89 LPC_SYSCON->SYSPLLCLKUEN = 0;
Pokitto 24:9561281d0378 90 while (LPC_SYSCON->SYSPLLCLKUEN & 0x00);
Pokitto 24:9561281d0378 91 LPC_SYSCON->SYSPLLCTRL = 0;
Pokitto 24:9561281d0378 92
Pokitto 24:9561281d0378 93 //kill peripherals
Pokitto 24:9561281d0378 94 LPC_SYSCON->MAINCLKSEL = 0;
Pokitto 24:9561281d0378 95 LPC_SYSCON->PRESETCTRL = 0; //disable all peripherals
Pokitto 24:9561281d0378 96
Pokitto 24:9561281d0378 97 //power down PLL
Pokitto 24:9561281d0378 98 volatile uint32_t tmp;
Pokitto 24:9561281d0378 99 tmp = (LPC_SYSCON->PDRUNCFG & 0x000025FFL);
Pokitto 24:9561281d0378 100 tmp |= ((1<<7) & 0x000025FFL);
Pokitto 24:9561281d0378 101 LPC_SYSCON->PDRUNCFG = (tmp | 0x0000C800L); /* Power-down SYSPLL */
Pokitto 24:9561281d0378 102
Pokitto 24:9561281d0378 103 //Chip_Clock_SetMainClockSource(SYSCTL_MAINCLKSRC_IRC); //switch to IRC
Pokitto 24:9561281d0378 104
Pokitto 24:9561281d0378 105 // clear all gpio states
Pokitto 24:9561281d0378 106 LPC_GPIO_PORT->PIN[0] = 0;
Pokitto 24:9561281d0378 107 LPC_GPIO_PORT->PIN[1] = 0;
Pokitto 24:9561281d0378 108 LPC_GPIO_PORT->PIN[2] = 0;
Pokitto 24:9561281d0378 109
Pokitto 24:9561281d0378 110 SCB->VTOR = app_link_location;//APPL_ADDRESS; /* Change vector table address */
Pokitto 24:9561281d0378 111 #ifndef __ARMCC_VERSION
Pokitto 24:9561281d0378 112 asm(" mov r0, %[address]"::[address] "r" (app_link_location));
Pokitto 24:9561281d0378 113 asm(" ldr r1, [r0,#0]"); // get the stack pointer value from the program's reset vector
Pokitto 24:9561281d0378 114 asm(" mov sp, r1"); // copy the value to the stack pointer
Pokitto 24:9561281d0378 115 asm(" ldr r0, [r0,#4]"); // get the program counter value from the program's reset vector
Pokitto 24:9561281d0378 116 asm(" blx r0"); // jump to the' start address
Pokitto 24:9561281d0378 117 #else
Pokitto 24:9561281d0378 118 uint32_t *app_loc = (uint32_t*)app_link_location;
Pokitto 24:9561281d0378 119 __set_MSP (app_loc[0]);
Pokitto 24:9561281d0378 120 ((func_t)(app_loc[1]))();
Pokitto 24:9561281d0378 121 #endif
Pokitto 24:9561281d0378 122 }
Pokitto 24:9561281d0378 123 #endif
Pokitto 24:9561281d0378 124
Pokitto 24:9561281d0378 125 // returns a random integar between 0 and maxVal
Pokitto 24:9561281d0378 126 int random(int maxVal)
Pokitto 24:9561281d0378 127 {
Pokitto 24:9561281d0378 128 return random( 0, maxVal);
Pokitto 24:9561281d0378 129 }
Pokitto 24:9561281d0378 130
Pokitto 24:9561281d0378 131 // returns a random integar between minVal and maxVal
Pokitto 24:9561281d0378 132 int random(int minVal, int maxVal)
Pokitto 24:9561281d0378 133 {
Pokitto 24:9561281d0378 134 // int rand(void); included by default from newlib
Pokitto 24:9561281d0378 135 return rand() % (maxVal-minVal+1) + minVal;
Pokitto 24:9561281d0378 136 }
Pokitto 24:9561281d0378 137
Pokitto 24:9561281d0378 138 using namespace Pokitto;
Pokitto 24:9561281d0378 139
Pokitto 24:9561281d0378 140 bool Core::run_state; // this definition needed
Pokitto 24:9561281d0378 141
Pokitto 24:9561281d0378 142 /** Components */
Pokitto 24:9561281d0378 143 Backlight Core::backlight;
Pokitto 24:9561281d0378 144 Buttons Core::buttons;
Pokitto 24:9561281d0378 145 Battery Core::battery;
Pokitto 24:9561281d0378 146 #if POK_ENABLE_SOUND > 0
Pokitto 24:9561281d0378 147 Sound Core::sound;
Pokitto 24:9561281d0378 148 #endif
Pokitto 24:9561281d0378 149 Display Core::display;
Pokitto 24:9561281d0378 150
Pokitto 24:9561281d0378 151 //GB Related
Pokitto 24:9561281d0378 152 uint8_t Core::startMenuTimer;
Pokitto 24:9561281d0378 153 uint8_t Core::timePerFrame;
Pokitto 24:9561281d0378 154 uint32_t Core::nextFrameMillis;
Pokitto 24:9561281d0378 155 uint32_t Core::frameCount;
Pokitto 24:9561281d0378 156 const char* Core::popupText;
Pokitto 24:9561281d0378 157 uint8_t Core::popupTimeLeft;
Pokitto 24:9561281d0378 158 uint16_t Core::frameDurationMicros;
Pokitto 24:9561281d0378 159 uint32_t Core::frameStartMicros, Core::frameEndMicros;
Pokitto 24:9561281d0378 160 uint8_t Core::volbar_visible=0;
Pokitto 24:9561281d0378 161
Pokitto 24:9561281d0378 162 uint32_t Core::fps_counter;
Pokitto 24:9561281d0378 163 uint32_t Core::fps_refreshtime;
Pokitto 24:9561281d0378 164 uint32_t Core::fps_frameCount;
Pokitto 24:9561281d0378 165
Pokitto 24:9561281d0378 166 Core::Core() {
Pokitto 24:9561281d0378 167
Pokitto 24:9561281d0378 168 }
Pokitto 24:9561281d0378 169
Pokitto 24:9561281d0378 170
Pokitto 24:9561281d0378 171 int Core::updateLoader (uint32_t version, uint32_t jumpaddress) {
Pokitto 24:9561281d0378 172 #ifndef POK_SIM
Pokitto 24:9561281d0378 173 uint32_t counter=0;
Pokitto 24:9561281d0378 174 uint8_t data[256];
Pokitto 24:9561281d0378 175 /** prepare the flash writing **/
Pokitto 24:9561281d0378 176 float progress=0;
Pokitto 24:9561281d0378 177 int opg=-1;
Pokitto 24:9561281d0378 178 uint32_t fsize=0;
Pokitto 24:9561281d0378 179 fileEnd(); //
Pokitto 24:9561281d0378 180 fsize = fileGetPosition();
Pokitto 24:9561281d0378 181 if (fsize>0x40000-jumpaddress) fsize = 0x40000-jumpaddress; // shouldn't happen!!
Pokitto 24:9561281d0378 182 fileRewind();
Pokitto 24:9561281d0378 183 display.println("PLEASE WAIT");
Pokitto 24:9561281d0378 184 while (1) {
Pokitto 24:9561281d0378 185 //if (counter >= fsize-0x200) {
Pokitto 24:9561281d0378 186 // display.println("gotcha");
Pokitto 24:9561281d0378 187 //}
Pokitto 24:9561281d0378 188 if (counter >= fsize) {
Pokitto 24:9561281d0378 189 break;
Pokitto 24:9561281d0378 190 }
Pokitto 24:9561281d0378 191 opg=progress;
Pokitto 24:9561281d0378 192 if (fileReadBytes(&data[0],0x100)<0x100) {
Pokitto 24:9561281d0378 193 if (fsize-counter>0x100) {
Pokitto 24:9561281d0378 194 display.println("ERROR READING LOA.DER FILE");
Pokitto 24:9561281d0378 195 return 1; // 1 means error
Pokitto 24:9561281d0378 196 }
Pokitto 24:9561281d0378 197 }
Pokitto 24:9561281d0378 198 if (CopyPageToFlash(jumpaddress+counter,data)) {
Pokitto 24:9561281d0378 199 display.println("FLASH WRITE ERROR");
Pokitto 24:9561281d0378 200 return 1;
Pokitto 24:9561281d0378 201 } else {
Pokitto 24:9561281d0378 202 counter += 0x100;
Pokitto 24:9561281d0378 203 display.print(".");
Pokitto 24:9561281d0378 204 }
Pokitto 24:9561281d0378 205 }
Pokitto 24:9561281d0378 206 #endif // POK_SIM
Pokitto 24:9561281d0378 207 return 0; //success
Pokitto 24:9561281d0378 208 }
Pokitto 24:9561281d0378 209
Pokitto 24:9561281d0378 210 void Core::showWarning() {
Pokitto 24:9561281d0378 211 display.enableDirectPrinting(true);
Pokitto 24:9561281d0378 212 display.directbgcolor = COLOR_BLACK;
Pokitto 24:9561281d0378 213 display.clearLCD();
Pokitto 24:9561281d0378 214 display.directcolor = COLOR_RED;
Pokitto 24:9561281d0378 215 display.setFont(fntC64UIGfx);
Pokitto 24:9561281d0378 216 display.adjustCharStep = 0;
Pokitto 24:9561281d0378 217 display.adjustLineStep = 0;
Pokitto 24:9561281d0378 218 display.setCursor(10*8,9);
Pokitto 24:9561281d0378 219 display.print("WARNING!");
Pokitto 24:9561281d0378 220 display.directcolor = COLOR_WHITE;
Pokitto 24:9561281d0378 221 display.setCursor(5*8,4*9);
Pokitto 24:9561281d0378 222 display.print("LOUD SOUND THROUGH");
Pokitto 24:9561281d0378 223 display.setCursor(2*8,5*9);
Pokitto 24:9561281d0378 224 display.print("HEADPHONES COULD DAMAGE");
Pokitto 24:9561281d0378 225 display.setCursor(7*8,6*9);
Pokitto 24:9561281d0378 226 display.print("YOUR HEARING.");
Pokitto 24:9561281d0378 227 display.setCursor(5*8,8*9);
Pokitto 24:9561281d0378 228 display.print("USE "); display.directcolor = COLOR_GREEN;
Pokitto 24:9561281d0378 229 display.print("0-100% VOLUME");
Pokitto 24:9561281d0378 230 display.directcolor = COLOR_WHITE;
Pokitto 24:9561281d0378 231 display.setCursor(5*8,9*9);
Pokitto 24:9561281d0378 232 display.print("FOR LISTENING WITH");
Pokitto 24:9561281d0378 233 display.setCursor(8*8,10*9);
Pokitto 24:9561281d0378 234 display.print("HEADPHONES");
Pokitto 24:9561281d0378 235 display.setCursor(5*8,12*9);
Pokitto 24:9561281d0378 236 display.print("USE "); display.directcolor = COLOR_RED;
Pokitto 24:9561281d0378 237 display.print("> 100% VOLUME"); display.directcolor = COLOR_GREEN;
Pokitto 24:9561281d0378 238 display.directcolor = COLOR_WHITE;
Pokitto 24:9561281d0378 239 display.setCursor(1*8,13*9);
Pokitto 24:9561281d0378 240 display.print("ONLY FOR LISTENING VIA THE");
Pokitto 24:9561281d0378 241 display.setCursor(5*8,14*9);
Pokitto 24:9561281d0378 242 display.print("BUILT-IN SPEAKER");
Pokitto 24:9561281d0378 243 display.setCursor(5*8,17*9);
Pokitto 24:9561281d0378 244 display.print("PRESS ");display.directcolor = COLOR_GREEN;
Pokitto 24:9561281d0378 245 display.print("C ");display.directcolor = COLOR_WHITE;
Pokitto 24:9561281d0378 246 display.print("TO ACCEPT");
Pokitto 24:9561281d0378 247 while (!buttons.cBtn()) {
Pokitto 24:9561281d0378 248 wait(100);
Pokitto 24:9561281d0378 249 }
Pokitto 24:9561281d0378 250 display.clearLCD();
Pokitto 24:9561281d0378 251 display.enableDirectPrinting(false);
Pokitto 24:9561281d0378 252 }
Pokitto 24:9561281d0378 253
Pokitto 24:9561281d0378 254 void Core::jumpToLoader() {
Pokitto 24:9561281d0378 255 //display.setFont(font5x7);
Pokitto 24:9561281d0378 256 //display.adjustCharStep=1;
Pokitto 24:9561281d0378 257 //display.adjustLineStep=2;
Pokitto 24:9561281d0378 258 display.fontSize=1;
Pokitto 24:9561281d0378 259 display.directbgcolor=COLOR_BLACK;
Pokitto 24:9561281d0378 260 display.directcolor=COLOR_GREEN;
Pokitto 24:9561281d0378 261 display.clearLCD();
Pokitto 24:9561281d0378 262 display.setCursor(0,0);
Pokitto 24:9561281d0378 263 display.enableDirectPrinting(true);
Pokitto 24:9561281d0378 264 #ifdef POK_SIM
Pokitto 24:9561281d0378 265 display.println("LOADER IS NOT AVAILABLE ON THE SIMULATOR. PRESS A TO RETURN.");
Pokitto 24:9561281d0378 266 #else
Pokitto 24:9561281d0378 267 uint32_t* bootinfo;
Pokitto 24:9561281d0378 268 uint32_t bootversion=0, sdversion=0, sdjump=0;
Pokitto 24:9561281d0378 269 bool flashloader=false, checkforboot=true;
Pokitto 24:9561281d0378 270 //check for loa.der on SD card
Pokitto 24:9561281d0378 271 #if POK_ENABLE_LOADER_UPDATES > 0
Pokitto 24:9561281d0378 272 pokInitSD();
Pokitto 24:9561281d0378 273 if (fileOpen("LOA.DER", FILE_MODE_BINARY)==0) {
Pokitto 24:9561281d0378 274 //LOA.DER found on SD
Pokitto 24:9561281d0378 275 fileEnd(); // go to end
Pokitto 24:9561281d0378 276 fileSeekRelative(-8); //rewind 8 bytes
Pokitto 24:9561281d0378 277 uint32_t* tptr = &sdversion;
Pokitto 24:9561281d0378 278 fileReadBytes((uint8_t*)tptr,4); //read version number of loader on SD card
Pokitto 24:9561281d0378 279 tptr = &sdjump;
Pokitto 24:9561281d0378 280 fileReadBytes((uint8_t*)tptr,4); //read jump address of loader on sd card
Pokitto 24:9561281d0378 281 fileRewind();
Pokitto 24:9561281d0378 282 }
Pokitto 24:9561281d0378 283 #endif
Pokitto 24:9561281d0378 284 //now start searching for bootkey
Pokitto 24:9561281d0378 285 while (checkforboot)
Pokitto 24:9561281d0378 286 {
Pokitto 24:9561281d0378 287 checkforboot=false; flashloader=false;
Pokitto 24:9561281d0378 288 bootinfo = (uint32_t*)0x3FFF4;
Pokitto 24:9561281d0378 289 if (*bootinfo != 0xB007AB1E) bootinfo = (uint32_t*)0x3FF04; //allow couple of alternative locations
Pokitto 24:9561281d0378 290 if (*bootinfo != 0xB007AB1E) bootinfo = (uint32_t*)0x3FE04; //allow couple of alternative locations
Pokitto 24:9561281d0378 291 if (*bootinfo != 0xB007AB1E) bootinfo = (uint32_t*)0x3F004; //for futureproofing
Pokitto 24:9561281d0378 292 if (*bootinfo != 0xB007AB1E) {
Pokitto 24:9561281d0378 293 // no bootkey found at all
Pokitto 24:9561281d0378 294 display.directcolor=COLOR_YELLOW;
Pokitto 24:9561281d0378 295 display.println("NO LOADER INSTALLED");
Pokitto 24:9561281d0378 296 if (sdversion==0 || sdjump < 0x38000) {
Pokitto 24:9561281d0378 297 //file open of loader failed
Pokitto 24:9561281d0378 298 display.println("NO VALID LOA.DER ON SD");
Pokitto 24:9561281d0378 299 display.println("");
Pokitto 24:9561281d0378 300 display.directcolor=COLOR_GREEN;
Pokitto 24:9561281d0378 301 display.println("PUT LOA.DER ON SD & REBOOT");
Pokitto 24:9561281d0378 302 } else flashloader=true;
Pokitto 24:9561281d0378 303 } else {
Pokitto 24:9561281d0378 304 //loader was found
Pokitto 24:9561281d0378 305 //check if we should update the loader
Pokitto 24:9561281d0378 306 display.directcolor=COLOR_CYAN;
Pokitto 24:9561281d0378 307 display.print("LOADER V.");
Pokitto 24:9561281d0378 308 display.directcolor=COLOR_WHITE;
Pokitto 24:9561281d0378 309 display.println(*(bootinfo+1));
Pokitto 24:9561281d0378 310 #if POK_ENABLE_LOADER_UPDATES
Pokitto 24:9561281d0378 311 if (sdversion>(*(bootinfo+1))) flashloader=true;
Pokitto 24:9561281d0378 312 else start_application(*(bootinfo+2)); //never returns
Pokitto 24:9561281d0378 313 #else
Pokitto 24:9561281d0378 314 start_application(*(bootinfo+2)); //never returns
Pokitto 24:9561281d0378 315 #endif
Pokitto 24:9561281d0378 316 }
Pokitto 24:9561281d0378 317 // update loader if it was requested
Pokitto 24:9561281d0378 318 if(flashloader) {
Pokitto 24:9561281d0378 319 display.directcolor=COLOR_MAGENTA;
Pokitto 24:9561281d0378 320 display.print("NEW LOADER ON SD V.");
Pokitto 24:9561281d0378 321 display.directcolor=COLOR_WHITE;
Pokitto 24:9561281d0378 322 display.println(sdversion);
Pokitto 24:9561281d0378 323 display.directcolor=COLOR_GREEN;
Pokitto 24:9561281d0378 324 display.println("UPDATE LOADER?\n(UP=YES, DOWN=CANCEL)");
Pokitto 24:9561281d0378 325 while(1) {
Pokitto 24:9561281d0378 326 if (buttons.upBtn()) {
Pokitto 24:9561281d0378 327 if (updateLoader(sdversion,sdjump)) {
Pokitto 24:9561281d0378 328 display.println("PUT LOA.DER ON SD AND RETRY");
Pokitto 24:9561281d0378 329 } else {
Pokitto 24:9561281d0378 330 display.println("SUCCESS!!");
Pokitto 24:9561281d0378 331 checkforboot=true; //recheck
Pokitto 24:9561281d0378 332 }
Pokitto 24:9561281d0378 333 break;
Pokitto 24:9561281d0378 334 }
Pokitto 24:9561281d0378 335 if (buttons.downBtn()) return;
Pokitto 24:9561281d0378 336 }
Pokitto 24:9561281d0378 337 } // if flashloader
Pokitto 24:9561281d0378 338 } // while checkforboot
Pokitto 24:9561281d0378 339 #endif // POK_SIM
Pokitto 24:9561281d0378 340 while (!buttons.aBtn()) {
Pokitto 24:9561281d0378 341 buttons.pollButtons();
Pokitto 24:9561281d0378 342 if (buttons.aBtn()) {
Pokitto 24:9561281d0378 343 while (buttons.aBtn()) {
Pokitto 24:9561281d0378 344 buttons.pollButtons();
Pokitto 24:9561281d0378 345 }
Pokitto 24:9561281d0378 346 return;
Pokitto 24:9561281d0378 347 }
Pokitto 24:9561281d0378 348 }
Pokitto 24:9561281d0378 349 }
Pokitto 24:9561281d0378 350
Pokitto 24:9561281d0378 351 void Core::askLoader() {
Pokitto 24:9561281d0378 352 display.enableDirectPrinting(true);
Pokitto 24:9561281d0378 353 display.directbgcolor = COLOR_BLACK;
Pokitto 24:9561281d0378 354 display.clearLCD();
Pokitto 24:9561281d0378 355 display.directcolor = COLOR_RED;
Pokitto 24:9561281d0378 356 display.setFont(fntC64UIGfx);
Pokitto 24:9561281d0378 357 display.fontSize=1;
Pokitto 24:9561281d0378 358 display.adjustCharStep = 0;
Pokitto 24:9561281d0378 359 display.adjustLineStep = 0;
Pokitto 24:9561281d0378 360 display.directcolor=COLOR_GREEN;
Pokitto 24:9561281d0378 361 display.set_cursor(12*8,6*8);
Pokitto 24:9561281d0378 362 display.print("ijkl");
Pokitto 24:9561281d0378 363 display.set_cursor(12*8,7*8);
Pokitto 24:9561281d0378 364 display.print("mnop");
Pokitto 24:9561281d0378 365 display.set_cursor(12*8,8*8);
Pokitto 24:9561281d0378 366 display.print("qrst");
Pokitto 24:9561281d0378 367 display.set_cursor(12*8,9*8);
Pokitto 24:9561281d0378 368 display.print("uvwx");
Pokitto 24:9561281d0378 369 display.set_cursor(5*8,12*8);
Pokitto 24:9561281d0378 370 display.print("PRESS");
Pokitto 24:9561281d0378 371 display.directcolor=COLOR_WHITE;
Pokitto 24:9561281d0378 372 display.print(" C ");
Pokitto 24:9561281d0378 373 display.directcolor=COLOR_GREEN;
Pokitto 24:9561281d0378 374 display.print("FOR LOADER");
Pokitto 24:9561281d0378 375 display.directcolor=COLOR_WHITE;
Pokitto 24:9561281d0378 376 display.fontSize=2;
Pokitto 24:9561281d0378 377 int countd=POK_LOADER_COUNTDOWN; uint16_t c2 = getTime();
Pokitto 24:9561281d0378 378 while (countd) {
Pokitto 24:9561281d0378 379 buttons.pollButtons();
Pokitto 24:9561281d0378 380 display.set_cursor(13*8,15*8);
Pokitto 24:9561281d0378 381 display.print(countd);
Pokitto 24:9561281d0378 382 if (getTime()>c2+1000) {
Pokitto 24:9561281d0378 383 c2=getTime();
Pokitto 24:9561281d0378 384 countd--;
Pokitto 24:9561281d0378 385 }
Pokitto 24:9561281d0378 386 if (cBtn()) {while (cBtn()) buttons.pollButtons();jumpToLoader();countd=0;}
Pokitto 24:9561281d0378 387 if (aBtn()) {while (aBtn()) buttons.pollButtons();countd=0;}
Pokitto 24:9561281d0378 388 if (bBtn()) {while (bBtn()) buttons.pollButtons();countd=0;}
Pokitto 24:9561281d0378 389 }
Pokitto 24:9561281d0378 390 display.fontSize=1;
Pokitto 24:9561281d0378 391 display.clearLCD();
Pokitto 24:9561281d0378 392 display.enableDirectPrinting(false);
Pokitto 24:9561281d0378 393 }
Pokitto 24:9561281d0378 394
Pokitto 24:9561281d0378 395
Pokitto 24:9561281d0378 396 void Core::drawvolbar(int x, int y, int level, bool text) {
Pokitto 24:9561281d0378 397 uint16_t oldcol = display.directcolor;
Pokitto 24:9561281d0378 398 if (text) display.directRectangle(0,0,50,50,COLOR_BLACK);
Pokitto 24:9561281d0378 399 display.directcolor = COLOR_GREEN;
Pokitto 24:9561281d0378 400 if (text) {
Pokitto 24:9561281d0378 401 bool temp = display.isDirectPrintingEnabled();
Pokitto 24:9561281d0378 402 display.enableDirectPrinting(true);
Pokitto 24:9561281d0378 403 display.print(x-1,y-20,(int)sound.getVolume());
Pokitto 24:9561281d0378 404 display.print(" ");
Pokitto 24:9561281d0378 405 display.enableDirectPrinting(temp);
Pokitto 24:9561281d0378 406 }
Pokitto 24:9561281d0378 407 if (level<12) display.directcolor = COLOR_GRAY_80;
Pokitto 24:9561281d0378 408 display.directBitmap(x,y,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 409 if (level<24) display.directcolor = COLOR_GRAY_80;
Pokitto 24:9561281d0378 410 display.directBitmap(x+8,y,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 411 display.directBitmap(x+8,y-4,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 412 display.directcolor = COLOR_RED;
Pokitto 24:9561281d0378 413 if (level<48) display.directcolor = COLOR_GRAY_80;
Pokitto 24:9561281d0378 414 display.directBitmap(x+16,y,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 415 display.directBitmap(x+16,y-4,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 416 display.directBitmap(x+16,y-8,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 417
Pokitto 24:9561281d0378 418 if (level<96) {
Pokitto 24:9561281d0378 419 display.directcolor = COLOR_GRAY_80;
Pokitto 24:9561281d0378 420 }
Pokitto 24:9561281d0378 421 display.directBitmap(x+24,y,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 422 display.directBitmap(x+24,y-4,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 423 display.directBitmap(x+24,y-8,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 424 display.directBitmap(x+24,y-12,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 425 if (level<160) {
Pokitto 24:9561281d0378 426 display.directcolor = COLOR_GRAY_80;
Pokitto 24:9561281d0378 427 }
Pokitto 24:9561281d0378 428 display.directBitmap(x+32,y,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 429 display.directBitmap(x+32,y-4,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 430 display.directBitmap(x+32,y-8,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 431 display.directBitmap(x+32,y-12,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 432 display.directBitmap(x+32,y-16,Pokitto_volumebar,1,1);
Pokitto 24:9561281d0378 433 display.directcolor = oldcol;
Pokitto 24:9561281d0378 434 }
Pokitto 24:9561281d0378 435
Pokitto 24:9561281d0378 436
Pokitto 24:9561281d0378 437 #ifdef POK_SIM
Pokitto 24:9561281d0378 438 #define VINCMULT 1
Pokitto 24:9561281d0378 439 #else
Pokitto 24:9561281d0378 440 #define VINCMULT 50
Pokitto 24:9561281d0378 441 #endif //POK_SIM
Pokitto 24:9561281d0378 442 void Core::setVolLimit() {
Pokitto 24:9561281d0378 443 display.enableDirectPrinting(true);
Pokitto 24:9561281d0378 444 display.adjustCharStep = 0;
Pokitto 24:9561281d0378 445 sound.setMaxVol(VOLUME_HEADPHONE_MAX);
Pokitto 24:9561281d0378 446 int dstate=1;
Pokitto 24:9561281d0378 447 bool wipe = true;
Pokitto 24:9561281d0378 448 float vol = sound.getVolume(); float tvol;
Pokitto 24:9561281d0378 449 volbar_visible=0;
Pokitto 24:9561281d0378 450 while (core.isRunning() && dstate){
Pokitto 24:9561281d0378 451 switch (dstate) {
Pokitto 24:9561281d0378 452 case 1:
Pokitto 24:9561281d0378 453 //redraw
Pokitto 24:9561281d0378 454 if (wipe) {
Pokitto 24:9561281d0378 455 display.clearLCD();
Pokitto 24:9561281d0378 456 display.directcolor = COLOR_WHITE;
Pokitto 24:9561281d0378 457 display.setCursor(4*8,2*8);
Pokitto 24:9561281d0378 458 display.print("SELECT VOLUME LIMIT");
Pokitto 24:9561281d0378 459 display.setCursor(5*8,17*9);
Pokitto 24:9561281d0378 460 display.print("PRESS ");
Pokitto 24:9561281d0378 461 display.directcolor = COLOR_GREEN;
Pokitto 24:9561281d0378 462 display.print("A");
Pokitto 24:9561281d0378 463 display.directcolor = COLOR_WHITE;
Pokitto 24:9561281d0378 464 display.print(" TO ACCEPT");
Pokitto 24:9561281d0378 465 display.directcolor = COLOR_GREEN;
Pokitto 24:9561281d0378 466 // draw frame below first
Pokitto 24:9561281d0378 467 display.setCursor(0,11*8);
Pokitto 24:9561281d0378 468 display.println(" abbbbbbbbbbbbbbbbbbbbbbbc");
Pokitto 24:9561281d0378 469 display.println(" | |");
Pokitto 24:9561281d0378 470 display.println(" | |");
Pokitto 24:9561281d0378 471 display.println(" | |");
Pokitto 24:9561281d0378 472 display.println(" | |");
Pokitto 24:9561281d0378 473 display.println(" dbbbbbbbbbbbbbbbbbbbbbbbe");
Pokitto 24:9561281d0378 474 } // wipe = true
Pokitto 24:9561281d0378 475 display.setCursor(6*8,17*9);
Pokitto 24:9561281d0378 476 if (sound.getVolume()-5<=VOLUME_HEADPHONE_MAX) display.directcolor = COLOR_WHITE;
Pokitto 24:9561281d0378 477 else display.directcolor = COLOR_RED;
Pokitto 24:9561281d0378 478 display.directBitmap(21*8-4,6*8,Pokitto_headphones,1,2);
Pokitto 24:9561281d0378 479 display.setCursor(3*8,6*8+6);
Pokitto 24:9561281d0378 480 display.print("HEADPHONES");
Pokitto 24:9561281d0378 481 display.setCursor(3*8,8*8+2);
Pokitto 24:9561281d0378 482 if (sound.getVolume()-8>VOLUME_HEADPHONE_MAX) display.print("TOO LOUD!");
Pokitto 24:9561281d0378 483 else display.print("OK ");
Pokitto 24:9561281d0378 484 display.directcolor = COLOR_GREEN;
Pokitto 24:9561281d0378 485 display.directBitmap(21*8-4,12*8,Pokitto_speaker,1,2);
Pokitto 24:9561281d0378 486 display.setCursor(3*8,12*8+6);
Pokitto 24:9561281d0378 487 display.print("VOLUME MAX");
Pokitto 24:9561281d0378 488 display.setCursor(3*8,14*8+2);
Pokitto 24:9561281d0378 489 tvol = (vol/float(VOLUME_HEADPHONE_MAX))*100;
Pokitto 24:9561281d0378 490 if (tvol > 100 && tvol < 120) tvol=100;
Pokitto 24:9561281d0378 491 if (sound.getVolume()-5>VOLUME_HEADPHONE_MAX) { display.directcolor=COLOR_RED;}
Pokitto 24:9561281d0378 492 else display.directcolor=COLOR_GREEN;
Pokitto 24:9561281d0378 493 display.print(int(sound.getVolume()));
Pokitto 24:9561281d0378 494 //display.print(int(tvol));
Pokitto 24:9561281d0378 495 display.print(" ");
Pokitto 24:9561281d0378 496 display.directcolor=COLOR_GREEN;
Pokitto 24:9561281d0378 497 drawvolbar(14*8,14*8+4+2,sound.getVolume(),false);
Pokitto 24:9561281d0378 498 //display.setCursor(1,10);
Pokitto 24:9561281d0378 499 //display.print(vol);
Pokitto 24:9561281d0378 500 dstate=2; break;
Pokitto 24:9561281d0378 501 case 2:
Pokitto 24:9561281d0378 502 buttons.pollButtons();
Pokitto 24:9561281d0378 503 if (aBtn()) {dstate=0;while(aBtn()){buttons.pollButtons();};break;}
Pokitto 24:9561281d0378 504 if (rightBtn()) {
Pokitto 24:9561281d0378 505 if (vol >= VOLUME_HEADPHONE_MAX && vol < VOLUME_HEADPHONE_MAX+1 ) vol += 0.00025f*VINCMULT;
Pokitto 24:9561281d0378 506 else if (vol >= VOLUME_HEADPHONE_MAX) vol += 0.025f*VINCMULT;
Pokitto 24:9561281d0378 507 else vol += 0.05f*VINCMULT;
Pokitto 24:9561281d0378 508 if (vol > VOLUME_HEADPHONE_MAX + 20) {
Pokitto 24:9561281d0378 509 sound.setMaxVol(VOLUME_SPEAKER_MAX);
Pokitto 24:9561281d0378 510 }
Pokitto 24:9561281d0378 511 if (vol > VOLUME_SPEAKER_MAX) vol=VOLUME_SPEAKER_MAX;
Pokitto 24:9561281d0378 512 sound.setVolume(vol);
Pokitto 24:9561281d0378 513 dstate=1; wipe=false;
Pokitto 24:9561281d0378 514 break;
Pokitto 24:9561281d0378 515 }
Pokitto 24:9561281d0378 516 if (leftBtn()) {
Pokitto 24:9561281d0378 517 vol -= 0.025f*VINCMULT;
Pokitto 24:9561281d0378 518 if (vol <= VOLUME_HEADPHONE_MAX) sound.setMaxVol(VOLUME_HEADPHONE_MAX);
Pokitto 24:9561281d0378 519 if (vol < 0) vol=0;
Pokitto 24:9561281d0378 520 sound.setVolume(vol);
Pokitto 24:9561281d0378 521 dstate=1; wipe=false;
Pokitto 24:9561281d0378 522 break;
Pokitto 24:9561281d0378 523 }
Pokitto 24:9561281d0378 524 break;
Pokitto 24:9561281d0378 525 }
Pokitto 24:9561281d0378 526 }
Pokitto 24:9561281d0378 527 }
Pokitto 24:9561281d0378 528
Pokitto 24:9561281d0378 529 void Core::begin() {
Pokitto 24:9561281d0378 530
Pokitto 24:9561281d0378 531 init(); // original functions
Pokitto 24:9561281d0378 532 timePerFrame = POK_FRAMEDURATION;
Pokitto 24:9561281d0378 533 //nextFrameMillis = 0;
Pokitto 24:9561281d0378 534 //frameCount = 0;
Pokitto 24:9561281d0378 535 frameEndMicros = 1;
Pokitto 24:9561281d0378 536 startMenuTimer = 255;
Pokitto 24:9561281d0378 537 //read default settings from flash memory (set using settings.hex)
Pokitto 24:9561281d0378 538 readSettings();
Pokitto 24:9561281d0378 539 //init everything
Pokitto 24:9561281d0378 540 backlight.begin();
Pokitto 24:9561281d0378 541 backlight.set(BACKLIGHT_MAX);
Pokitto 24:9561281d0378 542 buttons.begin();
Pokitto 24:9561281d0378 543 buttons.update();
Pokitto 24:9561281d0378 544 battery.begin();
Pokitto 24:9561281d0378 545 display.begin();
Pokitto 24:9561281d0378 546 #if POK_DISPLAYLOGO
Pokitto 24:9561281d0378 547 showLogo();
Pokitto 24:9561281d0378 548 #endif // POK_DISPLAYLOGO
Pokitto 24:9561281d0378 549
Pokitto 24:9561281d0378 550 display.enableDirectPrinting(true);
Pokitto 24:9561281d0378 551 display.directbgcolor = COLOR_BLACK;
Pokitto 24:9561281d0378 552 display.clearLCD();
Pokitto 24:9561281d0378 553 display.setFont(fntC64UIGfx);
Pokitto 24:9561281d0378 554
Pokitto 24:9561281d0378 555 display.enableDirectPrinting(true);
Pokitto 24:9561281d0378 556 display.directbgcolor = COLOR_BLACK;
Pokitto 24:9561281d0378 557 display.directcolor = COLOR_GREEN;
Pokitto 24:9561281d0378 558 display.clearLCD();
Pokitto 24:9561281d0378 559 display.setFont(fntC64UIGfx);
Pokitto 24:9561281d0378 560 display.adjustCharStep=0;
Pokitto 24:9561281d0378 561 display.adjustLineStep=1;
Pokitto 24:9561281d0378 562 #ifdef JUSTLOAD
Pokitto 24:9561281d0378 563 jumpToLoader();
Pokitto 24:9561281d0378 564 #endif
Pokitto 24:9561281d0378 565
Pokitto 24:9561281d0378 566 #ifndef DISABLE_LOADER
Pokitto 24:9561281d0378 567 askLoader();
Pokitto 24:9561281d0378 568 #endif
Pokitto 24:9561281d0378 569
Pokitto 24:9561281d0378 570 #ifndef DISABLE_SOUND_WARNING
Pokitto 24:9561281d0378 571 //showWarning();
Pokitto 24:9561281d0378 572 setVolLimit();
Pokitto 24:9561281d0378 573 //sound.setVolume(sound.getVolume());//make sure we're at set volume before continue
Pokitto 24:9561281d0378 574 sound.volumeUp();
Pokitto 24:9561281d0378 575 #endif
Pokitto 24:9561281d0378 576 display.enableDirectPrinting(false);
Pokitto 24:9561281d0378 577 display.adjustCharStep=1;
Pokitto 24:9561281d0378 578 display.adjustLineStep=1;
Pokitto 24:9561281d0378 579 display.fontSize=1;
Pokitto 24:9561281d0378 580 display.textWrap=true;
Pokitto 24:9561281d0378 581 #if POK_GAMEBUINO_SUPPORT > 0
Pokitto 24:9561281d0378 582 display.setFont(font5x7);
Pokitto 24:9561281d0378 583 #else
Pokitto 24:9561281d0378 584 display.setFont(fontC64);
Pokitto 24:9561281d0378 585 #endif
Pokitto 24:9561281d0378 586 #if POK_ENABLE_SOUND > 0
Pokitto 24:9561281d0378 587 sound.begin();
Pokitto 24:9561281d0378 588
Pokitto 24:9561281d0378 589 //mute when B is held during start up or if battery is low
Pokitto 24:9561281d0378 590 battery.update();
Pokitto 24:9561281d0378 591 if(buttons.pressed(BTN_B) || (battery.level == 0)){
Pokitto 24:9561281d0378 592 sound.setVolume(0);
Pokitto 24:9561281d0378 593 }
Pokitto 24:9561281d0378 594 else{ //play the startup sound on each channel for it to be louder
Pokitto 24:9561281d0378 595 #if POK_GBSOUND > 0
Pokitto 24:9561281d0378 596 #if(NUM_CHANNELS > 0)
Pokitto 24:9561281d0378 597 sound.playPattern(startupSound, 0);
Pokitto 24:9561281d0378 598 #endif
Pokitto 24:9561281d0378 599 #if(NUM_CHANNELS > 1)
Pokitto 24:9561281d0378 600 sound.playPattern(startupSound, 1);
Pokitto 24:9561281d0378 601 #endif
Pokitto 24:9561281d0378 602 #if(NUM_CHANNELS > 2)
Pokitto 24:9561281d0378 603 sound.playPattern(startupSound, 2);
Pokitto 24:9561281d0378 604 #endif
Pokitto 24:9561281d0378 605 #if(NUM_CHANNELS > 3)
Pokitto 24:9561281d0378 606 sound.playPattern(startupSound, 3);
Pokitto 24:9561281d0378 607 #endif
Pokitto 24:9561281d0378 608 #endif // POK_GBSOUND
Pokitto 24:9561281d0378 609 }
Pokitto 24:9561281d0378 610 #endif // POK ENABLE_SOUND
Pokitto 24:9561281d0378 611 }
Pokitto 24:9561281d0378 612
Pokitto 24:9561281d0378 613 void Core::init() {
Pokitto 24:9561281d0378 614 run_state = true;
Pokitto 24:9561281d0378 615 display.enableDirectPrinting(false);
Pokitto 24:9561281d0378 616 display.setFont(DEFAULT_FONT);
Pokitto 24:9561281d0378 617 initClock();
Pokitto 24:9561281d0378 618 initGPIO();
Pokitto 24:9561281d0378 619 initButtons();
Pokitto 24:9561281d0378 620 initRandom();
Pokitto 24:9561281d0378 621 //initAudio();
Pokitto 24:9561281d0378 622 //initDisplay();
Pokitto 24:9561281d0378 623 }
Pokitto 24:9561281d0378 624
Pokitto 24:9561281d0378 625 void Core::init(uint8_t switches) {
Pokitto 24:9561281d0378 626 run_state = true;
Pokitto 24:9561281d0378 627 display.enableDirectPrinting(false);
Pokitto 24:9561281d0378 628 display.setFont(DEFAULT_FONT);
Pokitto 24:9561281d0378 629 initClock();
Pokitto 24:9561281d0378 630 initGPIO();
Pokitto 24:9561281d0378 631 initButtons();
Pokitto 24:9561281d0378 632 initRandom();
Pokitto 24:9561281d0378 633 //initAudio();
Pokitto 24:9561281d0378 634 //initDisplay();
Pokitto 24:9561281d0378 635 }
Pokitto 24:9561281d0378 636
Pokitto 24:9561281d0378 637 void Core::initButtons() {
Pokitto 24:9561281d0378 638 #ifndef POK_SIM
Pokitto 24:9561281d0378 639 Pokitto::initButtons();
Pokitto 24:9561281d0378 640 #endif
Pokitto 24:9561281d0378 641 }
Pokitto 24:9561281d0378 642
Pokitto 24:9561281d0378 643 bool Core::isRunning() {
Pokitto 24:9561281d0378 644 #ifdef POK_SIM
Pokitto 24:9561281d0378 645 run_state = simulator.isRunning();
Pokitto 24:9561281d0378 646 #endif // POK_SIM
Pokitto 24:9561281d0378 647 return run_state;
Pokitto 24:9561281d0378 648 }
Pokitto 24:9561281d0378 649
Pokitto 24:9561281d0378 650 void Core::initDisplay() {
Pokitto 24:9561281d0378 651 #if POK_DISPLAYLOGO > 0
Pokitto 24:9561281d0378 652 showLogo();
Pokitto 24:9561281d0378 653 #endif
Pokitto 24:9561281d0378 654 #if POK_USE_CONSOLE > 0
Pokitto 24:9561281d0378 655 console.AddMessage(MSOURCE_LCD,MSG_INIT_OK);
Pokitto 24:9561281d0378 656 #endif
Pokitto 24:9561281d0378 657 }
Pokitto 24:9561281d0378 658
Pokitto 24:9561281d0378 659 void Core::showLogo() {
Pokitto 24:9561281d0378 660 uint32_t now;
Pokitto 24:9561281d0378 661 uint8_t state=0; //jump directly to logo, bypass teeth
Pokitto 24:9561281d0378 662 uint16_t counter=0, i=0;
Pokitto 24:9561281d0378 663 uint16_t sc;
Pokitto 24:9561281d0378 664 while (state < 255/6) {
Pokitto 24:9561281d0378 665 now=getTime();
Pokitto 24:9561281d0378 666 if (now>refreshtime) {
Pokitto 24:9561281d0378 667 refreshtime=now+30;
Pokitto 24:9561281d0378 668 switch (state) {
Pokitto 24:9561281d0378 669 case 0:
Pokitto 24:9561281d0378 670 /** POKITTO CLEAN **/
Pokitto 24:9561281d0378 671 display.directbgcolor = COLOR_BLACK;
Pokitto 24:9561281d0378 672 display.fillLCD(display.directbgcolor);
Pokitto 24:9561281d0378 673 sc = COLOR_BLACK;
Pokitto 24:9561281d0378 674 state++;
Pokitto 24:9561281d0378 675 break;
Pokitto 24:9561281d0378 676 case 1:
Pokitto 24:9561281d0378 677 /** POKITTO FADE IN **/
Pokitto 24:9561281d0378 678 display.directcolor = display.interpolateColor(sc, COLOR_GREEN, i);
Pokitto 24:9561281d0378 679 display.directBitmap(POK_LCD_W/2 - (*Pokitto_logo/2),POK_LCD_H/2-(*(Pokitto_logo+1)/2),Pokitto_logo,1,1);
Pokitto 24:9561281d0378 680 i += 28;
Pokitto 24:9561281d0378 681 if (i>=0xFF) { state++; i=0;}
Pokitto 24:9561281d0378 682 break;
Pokitto 24:9561281d0378 683 case 2:
Pokitto 24:9561281d0378 684 /** POKITTO WAIT **/
Pokitto 24:9561281d0378 685 display.directcolor = COLOR_GREEN;
Pokitto 24:9561281d0378 686 display.directBitmap(POK_LCD_W/2 - (*Pokitto_logo/2),POK_LCD_H/2-(*(Pokitto_logo+1)/2),Pokitto_logo,1,1);
Pokitto 24:9561281d0378 687 i+= 0x3F;
Pokitto 24:9561281d0378 688 if (i>0x3FF) state = 255;
Pokitto 24:9561281d0378 689 break;
Pokitto 24:9561281d0378 690 }
Pokitto 24:9561281d0378 691 if(buttons.aBtn()) state=255;
Pokitto 24:9561281d0378 692 }
Pokitto 24:9561281d0378 693 }
Pokitto 24:9561281d0378 694 }
Pokitto 24:9561281d0378 695
Pokitto 24:9561281d0378 696 void Core::readSettings() {
Pokitto 24:9561281d0378 697 // ToDo
Pokitto 24:9561281d0378 698 /*display.contrast = SCR_CONTRAST;
Pokitto 24:9561281d0378 699 backlight.backlightMin = BACKLIGHT_MIN;
Pokitto 24:9561281d0378 700 backlight.backlightMax = BACKLIGHT_MAX;
Pokitto 24:9561281d0378 701 backlight.ambientLightMin = AMBIENTLIGHT_MIN;
Pokitto 24:9561281d0378 702 backlight.ambientLightMax = AMBIENTLIGHT_MAX;
Pokitto 24:9561281d0378 703 */
Pokitto 24:9561281d0378 704 sound.setMaxVol(VOLUME_HEADPHONE_MAX);
Pokitto 24:9561281d0378 705 sound.globalVolume = VOLUME_STARTUP;
Pokitto 24:9561281d0378 706
Pokitto 24:9561281d0378 707 startMenuTimer = START_MENU_TIMER;
Pokitto 24:9561281d0378 708 /*
Pokitto 24:9561281d0378 709 battery.thresolds[0] = BAT_LVL_CRITIC;
Pokitto 24:9561281d0378 710 battery.thresolds[1] = BAT_LVL_LOW;
Pokitto 24:9561281d0378 711 battery.thresolds[2] = BAT_LVL_MED;
Pokitto 24:9561281d0378 712 battery.thresolds[3] = BAT_LVL_FULL;*/
Pokitto 24:9561281d0378 713 }
Pokitto 24:9561281d0378 714
Pokitto 24:9561281d0378 715 void Core::titleScreen(const char* name){
Pokitto 24:9561281d0378 716 titleScreen(name, 0);
Pokitto 24:9561281d0378 717 }
Pokitto 24:9561281d0378 718
Pokitto 24:9561281d0378 719 void Core::titleScreen(const uint8_t* logo){
Pokitto 24:9561281d0378 720 titleScreen((""), logo);
Pokitto 24:9561281d0378 721 }
Pokitto 24:9561281d0378 722
Pokitto 24:9561281d0378 723 void Core::titleScreen(){
Pokitto 24:9561281d0378 724 titleScreen((""));
Pokitto 24:9561281d0378 725 }
Pokitto 24:9561281d0378 726
Pokitto 24:9561281d0378 727 void Core::titleScreen(const char* name, const uint8_t *logo){
Pokitto 24:9561281d0378 728 display.setFont(font5x7);
Pokitto 24:9561281d0378 729 if(startMenuTimer){
Pokitto 24:9561281d0378 730 display.fontSize = 1;
Pokitto 24:9561281d0378 731 display.textWrap = false;
Pokitto 24:9561281d0378 732 display.persistence = false;
Pokitto 24:9561281d0378 733 battery.show = false;
Pokitto 24:9561281d0378 734 display.setColor(BLACK);
Pokitto 24:9561281d0378 735 while(isRunning()){
Pokitto 24:9561281d0378 736 if(update()){
Pokitto 24:9561281d0378 737 uint8_t logoOffset = name[0]?display.fontHeight:0; //add an offset the logo when there is a name to display
Pokitto 24:9561281d0378 738 //draw graphics
Pokitto 24:9561281d0378 739 display.setColorDepth(1);
Pokitto 24:9561281d0378 740 display.setColor(3);
Pokitto 24:9561281d0378 741 //display.drawBitmap(0,0, gamebuinoLogo);
Pokitto 24:9561281d0378 742 display.setColor(1);
Pokitto 24:9561281d0378 743 if(logo){
Pokitto 24:9561281d0378 744 display.drawBitmap(0, 12+logoOffset, logo);
Pokitto 24:9561281d0378 745 }
Pokitto 24:9561281d0378 746 display.cursorX = 0;
Pokitto 24:9561281d0378 747 display.cursorY = 12;
Pokitto 24:9561281d0378 748 display.print(name);
Pokitto 24:9561281d0378 749
Pokitto 24:9561281d0378 750 //A button
Pokitto 24:9561281d0378 751 display.cursorX = LCDWIDTH - display.fontWidth*3 -1;
Pokitto 24:9561281d0378 752 display.cursorY = LCDHEIGHT - display.fontHeight*3 - 3;
Pokitto 24:9561281d0378 753 if((frameCount/16)%2)
Pokitto 24:9561281d0378 754 display.println(("\25 \20"));
Pokitto 24:9561281d0378 755 else
Pokitto 24:9561281d0378 756 display.println(("\25\20 "));
Pokitto 24:9561281d0378 757 //B button
Pokitto 24:9561281d0378 758 display.cursorX = LCDWIDTH - display.fontWidth*3 - 1;
Pokitto 24:9561281d0378 759 display.cursorY++;
Pokitto 24:9561281d0378 760 if(sound.globalVolume)
Pokitto 24:9561281d0378 761 display.println(("\26\23\24"));
Pokitto 24:9561281d0378 762 else
Pokitto 24:9561281d0378 763 display.println(("\26\23x"));
Pokitto 24:9561281d0378 764 //C button
Pokitto 24:9561281d0378 765 display.cursorX = LCDWIDTH - display.fontWidth*3 - 1;
Pokitto 24:9561281d0378 766 display.cursorY++;
Pokitto 24:9561281d0378 767 //display.println(F("\27SD"));
Pokitto 24:9561281d0378 768
Pokitto 24:9561281d0378 769 //toggle volume when B is pressed
Pokitto 24:9561281d0378 770 if(buttons.pressed(BTN_B)){
Pokitto 24:9561281d0378 771 sound.setVolume(sound.getVolume() + 1);
Pokitto 24:9561281d0378 772 sound.playTick();
Pokitto 24:9561281d0378 773 }
Pokitto 24:9561281d0378 774 //leave the menu
Pokitto 24:9561281d0378 775 if(buttons.pressed(BTN_A) || ((frameCount>=startMenuTimer)&&(startMenuTimer != 255))){
Pokitto 24:9561281d0378 776 startMenuTimer = 255; //don't automatically skip the title screen next time it's displayed
Pokitto 24:9561281d0378 777 sound.stopPattern(0);
Pokitto 24:9561281d0378 778 sound.playOK();
Pokitto 24:9561281d0378 779 break;
Pokitto 24:9561281d0378 780 }
Pokitto 24:9561281d0378 781 //flash the loader
Pokitto 24:9561281d0378 782 //if(buttons.pressed(BTN_C))
Pokitto 24:9561281d0378 783 // ToDo changeGame();
Pokitto 24:9561281d0378 784 }
Pokitto 24:9561281d0378 785 }
Pokitto 24:9561281d0378 786 battery.show = true;
Pokitto 24:9561281d0378 787 }
Pokitto 24:9561281d0378 788 }
Pokitto 24:9561281d0378 789
Pokitto 24:9561281d0378 790 bool Core::update(bool useDirectMode) {
Pokitto 24:9561281d0378 791 #if POK_STREAMING_MUSIC
Pokitto 24:9561281d0378 792 sound.updateStream();
Pokitto 24:9561281d0378 793 #endif
Pokitto 24:9561281d0378 794
Pokitto 24:9561281d0378 795 uint32_t now = getTime();
Pokitto 24:9561281d0378 796 if ((((nextFrameMillis - now)) > timePerFrame) && frameEndMicros) { //if time to render a new frame is reached and the frame end has ran once
Pokitto 24:9561281d0378 797 nextFrameMillis = now + timePerFrame;
Pokitto 24:9561281d0378 798 frameCount++;
Pokitto 24:9561281d0378 799
Pokitto 24:9561281d0378 800 frameEndMicros = 0;
Pokitto 24:9561281d0378 801 backlight.update();
Pokitto 24:9561281d0378 802 buttons.update();
Pokitto 24:9561281d0378 803 battery.update();
Pokitto 24:9561281d0378 804
Pokitto 24:9561281d0378 805 // FPS counter
Pokitto 24:9561281d0378 806 #ifdef PROJ_USE_FPS_COUNTER
Pokitto 24:9561281d0378 807 const uint32_t fpsInterval_ms = 1000*3;
Pokitto 24:9561281d0378 808
Pokitto 24:9561281d0378 809 fps_frameCount++;
Pokitto 24:9561281d0378 810 if (now > fps_refreshtime) {
Pokitto 24:9561281d0378 811 fps_counter = (1000*fps_frameCount) / (now - fps_refreshtime + fpsInterval_ms);
Pokitto 24:9561281d0378 812 fps_refreshtime = now + fpsInterval_ms;
Pokitto 24:9561281d0378 813 fps_frameCount = 0;
Pokitto 24:9561281d0378 814 }
Pokitto 24:9561281d0378 815 #endif
Pokitto 24:9561281d0378 816
Pokitto 24:9561281d0378 817 return true;
Pokitto 24:9561281d0378 818
Pokitto 24:9561281d0378 819 } else {
Pokitto 24:9561281d0378 820 if (!frameEndMicros) { //runs once at the end of the frame
Pokitto 24:9561281d0378 821 #if POK_ENABLE_SOUND > 0
Pokitto 24:9561281d0378 822 sound.updateTrack();
Pokitto 24:9561281d0378 823 sound.updatePattern();
Pokitto 24:9561281d0378 824 sound.updateNote();
Pokitto 24:9561281d0378 825 #endif
Pokitto 24:9561281d0378 826 updatePopup();
Pokitto 24:9561281d0378 827 displayBattery();
Pokitto 24:9561281d0378 828
Pokitto 24:9561281d0378 829 display.update(useDirectMode); //send the buffer to the screen
Pokitto 24:9561281d0378 830
Pokitto 24:9561281d0378 831 frameEndMicros = 1; //jonne
Pokitto 24:9561281d0378 832
Pokitto 24:9561281d0378 833 }
Pokitto 24:9561281d0378 834 return false;
Pokitto 24:9561281d0378 835 }
Pokitto 24:9561281d0378 836 }
Pokitto 24:9561281d0378 837
Pokitto 24:9561281d0378 838 void Core::displayBattery(){
Pokitto 24:9561281d0378 839 #if (ENABLE_BATTERY > 0)
Pokitto 24:9561281d0378 840 //display.setColor(BLACK, WHITE);
Pokitto 24:9561281d0378 841 uint8_t ox,oy;
Pokitto 24:9561281d0378 842 ox=display.cursorX;
Pokitto 24:9561281d0378 843 oy=display.cursorY;
Pokitto 24:9561281d0378 844 display.cursorX = LCDWIDTH-display.fontWidth+1;
Pokitto 24:9561281d0378 845 display.cursorY = 0;
Pokitto 24:9561281d0378 846 switch(battery.level){
Pokitto 24:9561281d0378 847 case 0://battery critic, power down
Pokitto 24:9561281d0378 848 sound.stopPattern();
Pokitto 24:9561281d0378 849 backlight.set(0);
Pokitto 24:9561281d0378 850 display.clear();
Pokitto 24:9561281d0378 851 display.fontSize = 1;
Pokitto 24:9561281d0378 852 display.print(("LOW BATTERY\n"));
Pokitto 24:9561281d0378 853 display.print(battery.voltage);
Pokitto 24:9561281d0378 854 display.print(("mV\n\nPLEASE\nTURN OFF"));
Pokitto 24:9561281d0378 855 display.update();
Pokitto 24:9561281d0378 856 break;
Pokitto 24:9561281d0378 857 case 1: //empty battery
Pokitto 24:9561281d0378 858 if((frameCount % 16) < 8) display.print('\7'); //blinking battery
Pokitto 24:9561281d0378 859 else display.print('x');
Pokitto 24:9561281d0378 860 break;
Pokitto 24:9561281d0378 861 case 2://low battery
Pokitto 24:9561281d0378 862 case 3://full battery
Pokitto 24:9561281d0378 863 case 4://full battery
Pokitto 24:9561281d0378 864 if(battery.show){
Pokitto 24:9561281d0378 865 display.print(char(5+battery.level));
Pokitto 24:9561281d0378 866 }
Pokitto 24:9561281d0378 867 break;
Pokitto 24:9561281d0378 868 default:
Pokitto 24:9561281d0378 869 if(battery.show){
Pokitto 24:9561281d0378 870 display.print('/');
Pokitto 24:9561281d0378 871 }
Pokitto 24:9561281d0378 872 break;
Pokitto 24:9561281d0378 873 }
Pokitto 24:9561281d0378 874 display.cursorX = ox;
Pokitto 24:9561281d0378 875 display.cursorY = oy;
Pokitto 24:9561281d0378 876 #endif
Pokitto 24:9561281d0378 877 }
Pokitto 24:9561281d0378 878
Pokitto 24:9561281d0378 879 char* Core::filemenu(char *ext) {
Pokitto 24:9561281d0378 880 display.persistence = false;
Pokitto 24:9561281d0378 881 uint16_t oldpal0=display.palette[0];
Pokitto 24:9561281d0378 882 uint16_t oldpal1=display.palette[1];
Pokitto 24:9561281d0378 883 uint16_t oldpal2=display.palette[2];
Pokitto 24:9561281d0378 884 display.palette[2]=COLOR_GREEN;
Pokitto 24:9561281d0378 885 display.palette[1]=COLOR_WHITE;
Pokitto 24:9561281d0378 886 display.palette[0]=COLOR_BLACK;
Pokitto 24:9561281d0378 887 uint8_t oldbg=display.bgcolor;
Pokitto 24:9561281d0378 888 uint8_t oldfg=display.color;
Pokitto 24:9561281d0378 889 display.color=1;
Pokitto 24:9561281d0378 890 display.bgcolor=0;
Pokitto 24:9561281d0378 891
Pokitto 24:9561281d0378 892 int8_t activeItem = 0;
Pokitto 24:9561281d0378 893 int16_t currentY = 100;
Pokitto 24:9561281d0378 894 int16_t targetY = 0, rowh = display.fontHeight + 2;
Pokitto 24:9561281d0378 895 boolean exit = false;
Pokitto 24:9561281d0378 896
Pokitto 24:9561281d0378 897 char* txt;
Pokitto 24:9561281d0378 898
Pokitto 24:9561281d0378 899
Pokitto 24:9561281d0378 900 while (isRunning()) {
Pokitto 24:9561281d0378 901 if (update()) {
Pokitto 24:9561281d0378 902 getFirstFile(ext);
Pokitto 24:9561281d0378 903 if (buttons.pressed(BTN_A) || buttons.pressed(BTN_B) || buttons.pressed(BTN_C)) {
Pokitto 24:9561281d0378 904 exit = true; //time to exit menu !
Pokitto 24:9561281d0378 905 targetY = - display.fontHeight * 10 - 2; //send the menu out of the screen
Pokitto 24:9561281d0378 906 if (buttons.pressed(BTN_A)) {
Pokitto 24:9561281d0378 907 //answer = activeItem;
Pokitto 24:9561281d0378 908 sound.playOK();
Pokitto 24:9561281d0378 909 } else {
Pokitto 24:9561281d0378 910 sound.playCancel();
Pokitto 24:9561281d0378 911 }
Pokitto 24:9561281d0378 912 }
Pokitto 24:9561281d0378 913 if (exit == false) {
Pokitto 24:9561281d0378 914 if (buttons.repeat(BTN_DOWN,4)) {
Pokitto 24:9561281d0378 915 activeItem++;
Pokitto 24:9561281d0378 916 sound.playTick();
Pokitto 24:9561281d0378 917 }
Pokitto 24:9561281d0378 918 if (buttons.repeat(BTN_UP,4)) {
Pokitto 24:9561281d0378 919 activeItem--;
Pokitto 24:9561281d0378 920 sound.playTick();
Pokitto 24:9561281d0378 921 }
Pokitto 24:9561281d0378 922 //don't go out of the menu
Pokitto 24:9561281d0378 923 //if (activeItem == length) activeItem = 0;
Pokitto 24:9561281d0378 924 //if (activeItem < 0) activeItem = length - 1;
Pokitto 24:9561281d0378 925 if (currentY>targetY) currentY-=16;
Pokitto 24:9561281d0378 926 if (currentY<targetY) currentY=targetY;
Pokitto 24:9561281d0378 927 //targetY = -rowh * activeItem + (rowh+4); //center the menu on the active item
Pokitto 24:9561281d0378 928 } else { //exit :
Pokitto 24:9561281d0378 929 if (currentY>targetY) currentY-=16;
Pokitto 24:9561281d0378 930 if (currentY<targetY) currentY=targetY;
Pokitto 24:9561281d0378 931 if ((currentY - targetY) <= 1)
Pokitto 24:9561281d0378 932 {
Pokitto 24:9561281d0378 933 display.bgcolor=oldbg;
Pokitto 24:9561281d0378 934 display.color=oldfg;
Pokitto 24:9561281d0378 935 display.palette[0] = oldpal0;
Pokitto 24:9561281d0378 936 display.palette[1] = oldpal1;
Pokitto 24:9561281d0378 937 display.palette[2] = oldpal2;
Pokitto 24:9561281d0378 938 return selectedfile;
Pokitto 24:9561281d0378 939 }
Pokitto 24:9561281d0378 940
Pokitto 24:9561281d0378 941 }
Pokitto 24:9561281d0378 942 //draw a fancy menu
Pokitto 24:9561281d0378 943 //currentY = 0;//(currentY + targetY) / 2 + 5;
Pokitto 24:9561281d0378 944 display.cursorX = 0;
Pokitto 24:9561281d0378 945 display.cursorY = currentY;
Pokitto 24:9561281d0378 946 display.textWrap = false;
Pokitto 24:9561281d0378 947 uint16_t fc,bc;
Pokitto 24:9561281d0378 948 fc = display.color;
Pokitto 24:9561281d0378 949 bc = display.bgcolor;
Pokitto 24:9561281d0378 950 //getFirstFile(ext);
Pokitto 24:9561281d0378 951 for (int i = 0; i<20; i++) {
Pokitto 24:9561281d0378 952 display.invisiblecolor=255;
Pokitto 24:9561281d0378 953 display.cursorY = currentY + rowh * i;
Pokitto 24:9561281d0378 954 if (i==3) display.color=1;
Pokitto 24:9561281d0378 955 if (i == activeItem){
Pokitto 24:9561281d0378 956 display.cursorX = 3;
Pokitto 24:9561281d0378 957
Pokitto 24:9561281d0378 958 //display.fillRoundRect(0, currentY + display.fontHeight * activeItem - 2, LCDWIDTH, (display.fontHeight+3), 3);
Pokitto 24:9561281d0378 959 display.color=2;
Pokitto 24:9561281d0378 960 display.fillRect(0, currentY + rowh * activeItem - 2, LCDWIDTH, (rowh));
Pokitto 24:9561281d0378 961 display.setColor(0,2);
Pokitto 24:9561281d0378 962 } else display.setColor(1,0);
Pokitto 24:9561281d0378 963 //display.println((char*)*(const unsigned int*)(items+i));
Pokitto 24:9561281d0378 964 //display.println((int)i);
Pokitto 24:9561281d0378 965 txt = getNextFile(ext);
Pokitto 24:9561281d0378 966 if (txt) {
Pokitto 24:9561281d0378 967 display.println(txt);
Pokitto 24:9561281d0378 968 if (i == activeItem) {
Pokitto 24:9561281d0378 969 strcpy(selectedfile,txt);
Pokitto 24:9561281d0378 970 }
Pokitto 24:9561281d0378 971 } else i--;
Pokitto 24:9561281d0378 972 display.setColor(1,0);
Pokitto 24:9561281d0378 973 } // draw menu loop
Pokitto 24:9561281d0378 974 } // update
Pokitto 24:9561281d0378 975 }
Pokitto 24:9561281d0378 976 return 0;
Pokitto 24:9561281d0378 977 }
Pokitto 24:9561281d0378 978
Pokitto 24:9561281d0378 979 char* Core::filemenu() {
Pokitto 24:9561281d0378 980 return filemenu("");
Pokitto 24:9561281d0378 981 }
Pokitto 24:9561281d0378 982
Pokitto 24:9561281d0378 983 int8_t Core::menu(const char* const* items, uint8_t length) {
Pokitto 24:9561281d0378 984 #if (ENABLE_GUI > 0)
Pokitto 24:9561281d0378 985 display.persistence = false;
Pokitto 24:9561281d0378 986 int8_t activeItem = 0;
Pokitto 24:9561281d0378 987 int16_t currentY = display.height;
Pokitto 24:9561281d0378 988 int16_t targetY = 0, rowh = display.fontHeight + 2;
Pokitto 24:9561281d0378 989 boolean exit = false;
Pokitto 24:9561281d0378 990 int8_t answer = -1;
Pokitto 24:9561281d0378 991 while (isRunning()) {
Pokitto 24:9561281d0378 992 if (update()) {
Pokitto 24:9561281d0378 993 if (buttons.pressed(BTN_A) || buttons.pressed(BTN_B) || buttons.pressed(BTN_C)) {
Pokitto 24:9561281d0378 994 exit = true; //time to exit menu !
Pokitto 24:9561281d0378 995 targetY = - display.fontHeight * length - 2; //send the menu out of the screen
Pokitto 24:9561281d0378 996 if (buttons.pressed(BTN_A)) {
Pokitto 24:9561281d0378 997 answer = activeItem;
Pokitto 24:9561281d0378 998 sound.playOK();
Pokitto 24:9561281d0378 999 } else {
Pokitto 24:9561281d0378 1000 sound.playCancel();
Pokitto 24:9561281d0378 1001 }
Pokitto 24:9561281d0378 1002 }
Pokitto 24:9561281d0378 1003 if (exit == false) {
Pokitto 24:9561281d0378 1004 if (buttons.repeat(BTN_DOWN,4)) {
Pokitto 24:9561281d0378 1005 activeItem++;
Pokitto 24:9561281d0378 1006 sound.playTick();
Pokitto 24:9561281d0378 1007 }
Pokitto 24:9561281d0378 1008 if (buttons.repeat(BTN_UP,4)) {
Pokitto 24:9561281d0378 1009 activeItem--;
Pokitto 24:9561281d0378 1010 sound.playTick();
Pokitto 24:9561281d0378 1011 }
Pokitto 24:9561281d0378 1012 //don't go out of the menu
Pokitto 24:9561281d0378 1013 if (activeItem == length) activeItem = 0;
Pokitto 24:9561281d0378 1014 if (activeItem < 0) activeItem = length - 1;
Pokitto 24:9561281d0378 1015
Pokitto 24:9561281d0378 1016 targetY = -rowh * activeItem + (rowh+4); //center the menu on the active item
Pokitto 24:9561281d0378 1017 } else { //exit :
Pokitto 24:9561281d0378 1018 if ((currentY - targetY) <= 1)
Pokitto 24:9561281d0378 1019 return (answer);
Pokitto 24:9561281d0378 1020 }
Pokitto 24:9561281d0378 1021 //draw a fancy menu
Pokitto 24:9561281d0378 1022 currentY = (currentY + targetY) / 2;
Pokitto 24:9561281d0378 1023 display.cursorX = 0;
Pokitto 24:9561281d0378 1024 display.cursorY = currentY;
Pokitto 24:9561281d0378 1025 display.textWrap = false;
Pokitto 24:9561281d0378 1026 uint16_t fc,bc;
Pokitto 24:9561281d0378 1027 fc = display.color;
Pokitto 24:9561281d0378 1028 bc = display.bgcolor;
Pokitto 24:9561281d0378 1029 for (byte i = 0; i < length; i++) {
Pokitto 24:9561281d0378 1030 display.cursorY = currentY + rowh * i;
Pokitto 24:9561281d0378 1031 if (i == activeItem){
Pokitto 24:9561281d0378 1032 display.cursorX = 3;
Pokitto 24:9561281d0378 1033
Pokitto 24:9561281d0378 1034 //display.fillRoundRect(0, currentY + display.fontHeight * activeItem - 2, LCDWIDTH, (display.fontHeight+3), 3);
Pokitto 24:9561281d0378 1035 display.fillRect(0, currentY + rowh * activeItem - 2, LCDWIDTH, (rowh));
Pokitto 24:9561281d0378 1036 display.setColor(bc,fc);
Pokitto 24:9561281d0378 1037 } else display.setColor(fc,bc);
Pokitto 24:9561281d0378 1038
Pokitto 24:9561281d0378 1039 display.println((char*)*(const unsigned int*)(items+i));
Pokitto 24:9561281d0378 1040 display.setColor(fc,bc);
Pokitto 24:9561281d0378 1041 }
Pokitto 24:9561281d0378 1042
Pokitto 24:9561281d0378 1043 }
Pokitto 24:9561281d0378 1044 }
Pokitto 24:9561281d0378 1045 #else
Pokitto 24:9561281d0378 1046 return 0;
Pokitto 24:9561281d0378 1047 #endif
Pokitto 24:9561281d0378 1048 return 0;
Pokitto 24:9561281d0378 1049 }
Pokitto 24:9561281d0378 1050
Pokitto 24:9561281d0378 1051 void Core::keyboard(char* text, uint8_t length) {
Pokitto 24:9561281d0378 1052 #if (ENABLE_GUI > 0)
Pokitto 24:9561281d0378 1053 display.persistence = false;
Pokitto 24:9561281d0378 1054 //memset(text, 0, length); //clear the text
Pokitto 24:9561281d0378 1055 text[length-1] = '\0';
Pokitto 24:9561281d0378 1056 //active character in the typing area
Pokitto 24:9561281d0378 1057 int8_t activeChar = 0;
Pokitto 24:9561281d0378 1058 //selected char on the keyboard
Pokitto 24:9561281d0378 1059 int8_t activeX = 0;
Pokitto 24:9561281d0378 1060 int8_t activeY = 2;
Pokitto 24:9561281d0378 1061 //position of the keyboard on the screen
Pokitto 24:9561281d0378 1062 int8_t currentX = LCDWIDTH;
Pokitto 24:9561281d0378 1063 int8_t currentY = LCDHEIGHT;
Pokitto 24:9561281d0378 1064 int8_t targetX = 0;
Pokitto 24:9561281d0378 1065 int8_t targetY = 0;
Pokitto 24:9561281d0378 1066
Pokitto 24:9561281d0378 1067 while (1) {
Pokitto 24:9561281d0378 1068 if (update()) {
Pokitto 24:9561281d0378 1069 //move the character selector
Pokitto 24:9561281d0378 1070 if (buttons.repeat(BTN_DOWN, 4)) {
Pokitto 24:9561281d0378 1071 activeY++;
Pokitto 24:9561281d0378 1072 sound.playTick();
Pokitto 24:9561281d0378 1073 }
Pokitto 24:9561281d0378 1074 if (buttons.repeat(BTN_UP, 4)) {
Pokitto 24:9561281d0378 1075 activeY--;
Pokitto 24:9561281d0378 1076 sound.playTick();
Pokitto 24:9561281d0378 1077 }
Pokitto 24:9561281d0378 1078 if (buttons.repeat(BTN_RIGHT, 4)) {
Pokitto 24:9561281d0378 1079 activeX++;
Pokitto 24:9561281d0378 1080 sound.playTick();
Pokitto 24:9561281d0378 1081 }
Pokitto 24:9561281d0378 1082 if (buttons.repeat(BTN_LEFT, 4)) {
Pokitto 24:9561281d0378 1083 activeX--;
Pokitto 24:9561281d0378 1084 sound.playTick();
Pokitto 24:9561281d0378 1085 }
Pokitto 24:9561281d0378 1086 //don't go out of the keyboard
Pokitto 24:9561281d0378 1087 if (activeX == KEYBOARD_W) activeX = 0;
Pokitto 24:9561281d0378 1088 if (activeX < 0) activeX = KEYBOARD_W - 1;
Pokitto 24:9561281d0378 1089 if (activeY == KEYBOARD_H) activeY = 0;
Pokitto 24:9561281d0378 1090 if (activeY < 0) activeY = KEYBOARD_H - 1;
Pokitto 24:9561281d0378 1091 //set the keyboard position on screen
Pokitto 24:9561281d0378 1092 targetX = -(display.fontWidth+1) * activeX + LCDWIDTH / 2 - 3;
Pokitto 24:9561281d0378 1093 targetY = -(display.fontHeight+1) * activeY + LCDHEIGHT / 2 - 4 - display.fontHeight;
Pokitto 24:9561281d0378 1094 //smooth the keyboard displacement
Pokitto 24:9561281d0378 1095 currentX = (targetX + currentX) / 2;
Pokitto 24:9561281d0378 1096 currentY = (targetY + currentY) / 2;
Pokitto 24:9561281d0378 1097 //type character
Pokitto 24:9561281d0378 1098 if (buttons.pressed(BTN_A)) {
Pokitto 24:9561281d0378 1099 if (activeChar < (length-1)) {
Pokitto 24:9561281d0378 1100 byte thisChar = activeX + KEYBOARD_W * activeY;
Pokitto 24:9561281d0378 1101 if((thisChar == 0)||(thisChar == 10)||(thisChar == 13)) //avoid line feed and carriage return
Pokitto 24:9561281d0378 1102 continue;
Pokitto 24:9561281d0378 1103 text[activeChar] = thisChar;
Pokitto 24:9561281d0378 1104 text[activeChar+1] = '\0';
Pokitto 24:9561281d0378 1105 }
Pokitto 24:9561281d0378 1106 activeChar++;
Pokitto 24:9561281d0378 1107 sound.playOK();
Pokitto 24:9561281d0378 1108 if (activeChar > length)
Pokitto 24:9561281d0378 1109 activeChar = length;
Pokitto 24:9561281d0378 1110 }
Pokitto 24:9561281d0378 1111 //erase character
Pokitto 24:9561281d0378 1112 if (buttons.pressed(BTN_B)) {
Pokitto 24:9561281d0378 1113 activeChar--;
Pokitto 24:9561281d0378 1114 sound.playCancel();
Pokitto 24:9561281d0378 1115 if (activeChar >= 0)
Pokitto 24:9561281d0378 1116 text[activeChar] = 0;
Pokitto 24:9561281d0378 1117 else
Pokitto 24:9561281d0378 1118 activeChar = 0;
Pokitto 24:9561281d0378 1119 }
Pokitto 24:9561281d0378 1120 //leave menu
Pokitto 24:9561281d0378 1121 if (buttons.pressed(BTN_C)) {
Pokitto 24:9561281d0378 1122 sound.playOK();
Pokitto 24:9561281d0378 1123 while (1) {
Pokitto 24:9561281d0378 1124 if (update()) {
Pokitto 24:9561281d0378 1125 //display.setCursor(0,0);
Pokitto 24:9561281d0378 1126 display.println(("You entered\n"));
Pokitto 24:9561281d0378 1127 display.print(text);
Pokitto 24:9561281d0378 1128 display.println(("\n\n\n\x15:okay \x16:edit"));
Pokitto 24:9561281d0378 1129 if(buttons.pressed(BTN_A)){
Pokitto 24:9561281d0378 1130 sound.playOK();
Pokitto 24:9561281d0378 1131 return;
Pokitto 24:9561281d0378 1132 }
Pokitto 24:9561281d0378 1133 if(buttons.pressed(BTN_B)){
Pokitto 24:9561281d0378 1134 sound.playCancel();
Pokitto 24:9561281d0378 1135 break;
Pokitto 24:9561281d0378 1136 }
Pokitto 24:9561281d0378 1137 }
Pokitto 24:9561281d0378 1138 }
Pokitto 24:9561281d0378 1139 }
Pokitto 24:9561281d0378 1140 //draw the keyboard
Pokitto 24:9561281d0378 1141 for (int8_t y = 0; y < KEYBOARD_H; y++) {
Pokitto 24:9561281d0378 1142 for (int8_t x = 0; x < KEYBOARD_W; x++) {
Pokitto 24:9561281d0378 1143 display.drawChar(currentX + x * (display.fontWidth+1), currentY + y * (display.fontHeight+1), x + y * KEYBOARD_W, 1);
Pokitto 24:9561281d0378 1144 }
Pokitto 24:9561281d0378 1145 }
Pokitto 24:9561281d0378 1146 //draw instruction
Pokitto 24:9561281d0378 1147 display.cursorX = currentX-display.fontWidth*6-2;
Pokitto 24:9561281d0378 1148 display.cursorY = currentY+1*(display.fontHeight+1);
Pokitto 24:9561281d0378 1149 display.print(("\25type"));
Pokitto 24:9561281d0378 1150
Pokitto 24:9561281d0378 1151 display.cursorX = currentX-display.fontWidth*6-2;
Pokitto 24:9561281d0378 1152 display.cursorY = currentY+2*(display.fontHeight+1);
Pokitto 24:9561281d0378 1153 display.print(("\26back"));
Pokitto 24:9561281d0378 1154
Pokitto 24:9561281d0378 1155 display.cursorX = currentX-display.fontWidth*6-2;
Pokitto 24:9561281d0378 1156 display.cursorY = currentY+3*(display.fontHeight+1);
Pokitto 24:9561281d0378 1157 display.print(("\27save"));
Pokitto 24:9561281d0378 1158
Pokitto 24:9561281d0378 1159 //erase some pixels around the selected character
Pokitto 24:9561281d0378 1160 display.setColor(WHITE);
Pokitto 24:9561281d0378 1161 display.drawFastHLine(currentX + activeX * (display.fontWidth+1) - 1, currentY + activeY * (display.fontHeight+1) - 2, 7);
Pokitto 24:9561281d0378 1162 //draw the selection rectangle
Pokitto 24:9561281d0378 1163 display.setColor(BLACK);
Pokitto 24:9561281d0378 1164 display.drawRoundRect(currentX + activeX * (display.fontWidth+1) - 2, currentY + activeY * (display.fontHeight+1) - 3, (display.fontWidth+2)+(display.fontWidth-1)%2, (display.fontHeight+5), 3);
Pokitto 24:9561281d0378 1165 //draw keyboard outline
Pokitto 24:9561281d0378 1166 //display.drawRoundRect(currentX - 6, currentY - 6, KEYBOARD_W * (display.fontWidth+1) + 12, KEYBOARD_H * (display.fontHeight+1) + 12, 8, BLACK);
Pokitto 24:9561281d0378 1167 //text field
Pokitto 24:9561281d0378 1168 display.drawFastHLine(0, LCDHEIGHT-display.fontHeight-2, LCDWIDTH);
Pokitto 24:9561281d0378 1169 display.setColor(WHITE);
Pokitto 24:9561281d0378 1170 display.fillRect(0, LCDHEIGHT-display.fontHeight-1, LCDWIDTH, display.fontHeight+1);
Pokitto 24:9561281d0378 1171 //typed text
Pokitto 24:9561281d0378 1172 display.cursorX = 0;
Pokitto 24:9561281d0378 1173 display.cursorY = LCDHEIGHT-display.fontHeight;
Pokitto 24:9561281d0378 1174 display.setColor(BLACK);
Pokitto 24:9561281d0378 1175 display.print(text);
Pokitto 24:9561281d0378 1176 //blinking cursor
Pokitto 24:9561281d0378 1177 if (((frameCount % 8) < 4) && (activeChar < (length-1)))
Pokitto 24:9561281d0378 1178 display.drawChar(display.fontWidth * activeChar, LCDHEIGHT-display.fontHeight, '_',1);
Pokitto 24:9561281d0378 1179 }
Pokitto 24:9561281d0378 1180 }
Pokitto 24:9561281d0378 1181 #endif
Pokitto 24:9561281d0378 1182 }
Pokitto 24:9561281d0378 1183
Pokitto 24:9561281d0378 1184 void Core::popup(const char* text, uint8_t duration){
Pokitto 24:9561281d0378 1185 #if (ENABLE_GUI > 0)
Pokitto 24:9561281d0378 1186 popupText = text;
Pokitto 24:9561281d0378 1187 popupTimeLeft = duration+12;
Pokitto 24:9561281d0378 1188 #endif
Pokitto 24:9561281d0378 1189 }
Pokitto 24:9561281d0378 1190
Pokitto 24:9561281d0378 1191 void Core::updatePopup(){
Pokitto 24:9561281d0378 1192 #if (ENABLE_GUI > 0)
Pokitto 24:9561281d0378 1193 if (popupTimeLeft){
Pokitto 24:9561281d0378 1194 uint8_t yOffset = 0;
Pokitto 24:9561281d0378 1195 if(popupTimeLeft<12){
Pokitto 24:9561281d0378 1196 yOffset = 12-popupTimeLeft;
Pokitto 24:9561281d0378 1197 }
Pokitto 24:9561281d0378 1198 display.fontSize = 1;
Pokitto 24:9561281d0378 1199 display.setColor(WHITE);
Pokitto 24:9561281d0378 1200 display.fillRoundRect(0,LCDHEIGHT-display.fontHeight+yOffset-3,84,display.fontHeight+3,3);
Pokitto 24:9561281d0378 1201 display.setColor(BLACK);
Pokitto 24:9561281d0378 1202 display.drawRoundRect(0,LCDHEIGHT-display.fontHeight+yOffset-3,84,display.fontHeight+3,3);
Pokitto 24:9561281d0378 1203 display.cursorX = 4;
Pokitto 24:9561281d0378 1204 display.cursorY = LCDHEIGHT-display.fontHeight+yOffset-1;
Pokitto 24:9561281d0378 1205 display.print(popupText);
Pokitto 24:9561281d0378 1206 popupTimeLeft--;
Pokitto 24:9561281d0378 1207 }
Pokitto 24:9561281d0378 1208 #endif
Pokitto 24:9561281d0378 1209 }
Pokitto 24:9561281d0378 1210
Pokitto 24:9561281d0378 1211 void Core::setFrameRate(uint8_t fps) {
Pokitto 24:9561281d0378 1212 timePerFrame = 1000 / fps;
Pokitto 24:9561281d0378 1213 sound.prescaler = fps / 20;
Pokitto 24:9561281d0378 1214 sound.prescaler = __avrmax(1, sound.prescaler);
Pokitto 24:9561281d0378 1215 }
Pokitto 24:9561281d0378 1216
Pokitto 24:9561281d0378 1217 void Core::pickRandomSeed(){
Pokitto 24:9561281d0378 1218 initRandom();
Pokitto 24:9561281d0378 1219 }
Pokitto 24:9561281d0378 1220
Pokitto 24:9561281d0378 1221 bool Core::collidePointRect(int16_t x1, int16_t y1 ,int16_t x2 ,int16_t y2, int16_t w, int16_t h){
Pokitto 24:9561281d0378 1222 if((x1>=x2)&&(x1<x2+w))
Pokitto 24:9561281d0378 1223 if((y1>=y2)&&(y1<y2+h))
Pokitto 24:9561281d0378 1224 return true;
Pokitto 24:9561281d0378 1225 return false;
Pokitto 24:9561281d0378 1226 }
Pokitto 24:9561281d0378 1227
Pokitto 24:9561281d0378 1228 bool Core::collideRectRect(int16_t x1, int16_t y1, int16_t w1, int16_t h1 ,int16_t x2 ,int16_t y2, int16_t w2, int16_t h2){
Pokitto 24:9561281d0378 1229 return !( x2 >= x1+w1 ||
Pokitto 24:9561281d0378 1230 x2+w2 <= x1 ||
Pokitto 24:9561281d0378 1231 y2 >= y1+h1 ||
Pokitto 24:9561281d0378 1232 y2+h2 <= y1 );
Pokitto 24:9561281d0378 1233 }
Pokitto 24:9561281d0378 1234
Pokitto 24:9561281d0378 1235 bool Core::collideBitmapBitmap(int16_t x1, int16_t y1, const uint8_t* b1, int16_t x2, int16_t y2, const uint8_t* b2){
Pokitto 24:9561281d0378 1236 int16_t w1 = pgm_read_byte(b1);
Pokitto 24:9561281d0378 1237 int16_t h1 = pgm_read_byte(b1 + 1);
Pokitto 24:9561281d0378 1238 int16_t w2 = pgm_read_byte(b2);
Pokitto 24:9561281d0378 1239 int16_t h2 = pgm_read_byte(b2 + 1);
Pokitto 24:9561281d0378 1240
Pokitto 24:9561281d0378 1241 if(collideRectRect(x1, y1, w1, h1, x2, y2, w2, h2) == false){
Pokitto 24:9561281d0378 1242 return false;
Pokitto 24:9561281d0378 1243 }
Pokitto 24:9561281d0378 1244
Pokitto 24:9561281d0378 1245 int16_t xmin = (x1>=x2)? 0 : x2-x1;
Pokitto 24:9561281d0378 1246 int16_t ymin = (y1>=y2)? 0 : y2-y1;
Pokitto 24:9561281d0378 1247 int16_t xmax = (x1+w1>=x2+w2)? x2+w2-x1 : w1;
Pokitto 24:9561281d0378 1248 int16_t ymax = (y1+h1>=y2+h2)? y2+h2-y1 : h1;
Pokitto 24:9561281d0378 1249 for(uint8_t y = ymin; y < ymax; y++){
Pokitto 24:9561281d0378 1250 for(uint8_t x = xmin; x < xmax; x++){
Pokitto 24:9561281d0378 1251 if(display.getBitmapPixel(b1, x, y) && display.getBitmapPixel(b2, x1+x-x2, y1+y-y2)){
Pokitto 24:9561281d0378 1252 return true;
Pokitto 24:9561281d0378 1253 }
Pokitto 24:9561281d0378 1254 }
Pokitto 24:9561281d0378 1255 }
Pokitto 24:9561281d0378 1256 return false;
Pokitto 24:9561281d0378 1257 }
Pokitto 24:9561281d0378 1258
Pokitto 24:9561281d0378 1259
Pokitto 24:9561281d0378 1260 //** EOF **//
Pokitto 24:9561281d0378 1261
Pokitto 24:9561281d0378 1262
Pokitto 24:9561281d0378 1263
Pokitto 24:9561281d0378 1264
Pokitto 24:9561281d0378 1265
Pokitto 24:9561281d0378 1266
Pokitto 24:9561281d0378 1267
Pokitto 24:9561281d0378 1268
Pokitto 24:9561281d0378 1269
Pokitto 24:9561281d0378 1270