emuapi.cpp
1 #define KEYMAP_PRESENT 1 2 3 //extern "C" { 4 #include "emuapi.h" 5 #include "iopins.h" 6 //} 7 8 #include "tft_t_dma.h" 9 //#include "logo.h" 10 #include "bmpjoy.h" 11 #include "bmpvbar.h" 12 #ifdef OLD_LAYOUT 13 #include "bmpvga.h" 14 #include "bmptft.h" 15 #endif 16 17 18 #ifdef HAS_I2CKBD 19 #include <Wire.h> 20 #endif 21 22 #ifdef USE_SDFS 23 #include "uSDFS.h" 24 static FATFS fatfs; 25 static FIL file; 26 #else 27 28 #ifdef USE_SDFAT 29 #include "SdFat.h" 30 #include "sdios.h" 31 32 #ifndef SDCARD_SS_PIN 33 const uint8_t SD_CS_PIN = SS; 34 35 #else // SDCARD_SS_PIN 36 // Assume built-in SD is used. 37 const uint8_t SD_CS_PIN = SDCARD_SS_PIN; 38 #endif // SDCARD_SS_PIN 39 40 #define SD_CONFIG SdioConfig(FIFO_SDIO) 41 42 // Try to select the best SD card configuration. 43 #if HAS_SDIO_CLASS 44 #define SD_CONFIG SdioConfig(FIFO_SDIO) 45 #elif ENABLE_DEDICATED_SPI 46 #define SD_CONFIG SdSpiConfig(SD_CS_PIN, DEDICATED_SPI) 47 #else // HAS_SDIO_CLASS 48 #define SD_CONFIG SdSpiConfig(SD_CS_PIN, SHARED_SPI) 49 #endif // HAS_SDIO_CLASS 50 //------------------------------------------------------------------------------ 51 52 #if SD_FAT_TYPE == 0 53 #elif SD_FAT_TYPE == 1 54 #define SdFat SdFat32 55 #define File File32 56 #elif SD_FAT_TYPE == 2 57 #define SdFat SdExFat 58 #define File ExFile 59 #elif SD_FAT_TYPE == 3 60 #define SdFat SdFs 61 #define File FsFile 62 #endif // SD_FAT_TYPE 63 static SdFat SD; 64 #else 65 #include <SD.h> 66 #endif 67 static File file; 68 #endif 69 70 #define CALIBRATION_FILE "/cal.cfg" 71 72 #define MKEY_L1 1 73 #define MKEY_L2 2 74 #define MKEY_L3 3 75 #define MKEY_L4 4 76 #define MKEY_L5 5 77 #define MKEY_L6 6 78 #define MKEY_L7 7 79 #define MKEY_L8 8 80 #define MKEY_L9 9 81 #define MKEY_UP 20 82 #define MKEY_DOWN 21 83 #define MKEY_JOY 22 84 #define MKEY_TFT 23 85 #define MKEY_VGA 24 86 87 #define MAX_FILES 32 88 #define MAX_FILENAME_SIZE 24 89 #define MAX_MENULINES (MKEY_L9) 90 #define TEXT_HEIGHT 16 91 #define TEXT_WIDTH 8 92 #define MENU_FILE_XOFFSET (6*TEXT_WIDTH) 93 #define MENU_FILE_YOFFSET (2*TEXT_HEIGHT) 94 #define MENU_FILE_W (MAX_FILENAME_SIZE*TEXT_WIDTH) 95 #define MENU_FILE_H (MAX_MENULINES*TEXT_HEIGHT) 96 #define MENU_FILE_BGCOLOR RGBVAL16(0x00,0x00,0x20) 97 #define MENU_JOYS_YOFFSET (12*TEXT_HEIGHT) 98 #define MENU_VBAR_XOFFSET (0*TEXT_WIDTH) 99 #define MENU_VBAR_YOFFSET (MENU_FILE_YOFFSET) 100 101 #define MENU_TFT_XOFFSET (MENU_FILE_XOFFSET+MENU_FILE_W+8) 102 #define MENU_TFT_YOFFSET (MENU_VBAR_YOFFSET+32) 103 #define MENU_VGA_XOFFSET (MENU_FILE_XOFFSET+MENU_FILE_W+8) 104 #define MENU_VGA_YOFFSET (MENU_VBAR_YOFFSET+MENU_FILE_H-32-37) 105 106 extern TFT_T_DMA tft; 107 108 static char romspath[64]; 109 static int nbFiles=0; 110 static int curFile=0; 111 static int topFile=0; 112 static char selection[MAX_FILENAME_SIZE+1]=""; 113 static char files[MAX_FILES][MAX_FILENAME_SIZE]; 114 static bool menuRedraw=true; 115 116 static int16_t calMinX=-1,calMinY=-1,calMaxX=-1,calMaxY=-1; 117 static bool i2cKeyboardPresent = false; 118 const uint16_t deflogo[] = { 119 0x0000,0x0000 120 }; 121 static const uint16_t * logo = deflogo; 122 static unsigned short * keys; 123 static int keyMap; 124 125 126 const unsigned short menutouchareas[] = { 127 TAREA_XY,MENU_FILE_XOFFSET,MENU_FILE_YOFFSET, 128 TAREA_WH,MENU_FILE_W, TEXT_HEIGHT, 129 TAREA_NEW_COL,TEXT_HEIGHT,TEXT_HEIGHT,TEXT_HEIGHT,TEXT_HEIGHT,TEXT_HEIGHT,TEXT_HEIGHT,TEXT_HEIGHT,TEXT_HEIGHT,TEXT_HEIGHT, 130 131 TAREA_XY,MENU_VBAR_XOFFSET,MENU_VBAR_YOFFSET, 132 TAREA_WH,32,48, 133 TAREA_NEW_COL, 72,72,8,40, 134 135 TAREA_XY,MENU_TFT_XOFFSET,MENU_TFT_YOFFSET, 136 TAREA_WH,32,37, 137 TAREA_NEW_COL, 38,38, 138 139 TAREA_END}; 140 141 const unsigned short menutouchactions[] = { 142 MKEY_L1,MKEY_L2,MKEY_L3,MKEY_L4,MKEY_L5,MKEY_L6,MKEY_L7,MKEY_L8,MKEY_L9, 143 MKEY_UP,MKEY_DOWN,ACTION_NONE,MKEY_JOY, 144 MKEY_TFT,MKEY_VGA}; 145 146 147 static int keypadval=0; 148 static boolean joySwapped = false; 149 static uint16_t bLastState; 150 static int xRef; 151 static int yRef; 152 static uint8_t prev_zt=0; 153 154 static bool menuOn=true; 155 static bool callibrationOn=false; 156 static int callibrationStep=0; 157 158 159 static char captureTouchZone(const unsigned short * areas, const unsigned short * actions, int *rx, int *ry, int *rw, int * rh) { 160 uint16_t xt=0; 161 uint16_t yt=0; 162 uint16_t zt=0; 163 boolean hDir=true; 164 165 if (tft.isTouching()) 166 { 167 if (prev_zt == 0) { 168 prev_zt =1; 169 tft.readCal(&xt,&yt,&zt); 170 if (zt<1000) { 171 prev_zt=0; 172 return ACTION_NONE; 173 } 174 int i=0; 175 int k=0; 176 int y2=0, y1=0; 177 int x2=0, x1=0; 178 int x=KEYBOARD_X,y=KEYBOARD_Y; 179 int w=TAREA_W_DEF,h=TAREA_H_DEF; 180 uint8_t s; 181 while ( (s=areas[i++]) != TAREA_END ) { 182 if (s == TAREA_XY) { 183 x = areas[i++]; 184 y = areas[i++]; 185 x2 = x; 186 y2 = y; 187 } 188 else if (s == TAREA_WH) { 189 w = areas[i++]; 190 h = areas[i++]; 191 } 192 else if (s == TAREA_NEW_ROW) { 193 hDir = true; 194 y1 = y2; 195 y2 = y1 + h; 196 x2 = x; 197 } 198 else if (s == TAREA_NEW_COL) { 199 hDir = false; 200 x1 = x2; 201 x2 = x1 + w; 202 y2 = y; 203 } 204 else { 205 if (hDir) { 206 x1 = x2; 207 x2 = x1+s; 208 } else { 209 y1 = y2; 210 y2 = y1+s; 211 } 212 if ( (yt >= y1) && (yt < y2) && (xt >= x1) && (xt < x2) ) { 213 *rx = x1; 214 *ry = y1; 215 *rw = x2-x1; 216 *rh = y2-y1; 217 return (actions[k]); 218 } 219 k++; 220 } 221 } 222 } 223 prev_zt =1; 224 } else { 225 prev_zt=0; 226 } 227 228 return ACTION_NONE; 229 } 230 231 232 233 234 235 236 237 238 void emu_printf(char * text) 239 { 240 Serial.println(text); 241 } 242 243 void emu_printf(int val) 244 { 245 Serial.println(val); 246 } 247 248 void emu_printi(int val) 249 { 250 Serial.println(val); 251 } 252 253 void emu_printh(int val) 254 { 255 Serial.println(val,HEX); 256 } 257 258 static int malbufpt = 0; 259 static char malbuf[EXTRA_HEAP]; 260 261 void * emu_Malloc(int size) 262 { 263 void * retval = malloc(size); 264 if (!retval) { 265 emu_printf("failled to allocate"); 266 emu_printf(size); 267 emu_printf("fallback"); 268 if ( (malbufpt+size) < sizeof(malbuf) ) { 269 retval = (void *)&malbuf[malbufpt]; 270 malbufpt += size; 271 } 272 else { 273 emu_printf("failure to allocate"); 274 } 275 } 276 else { 277 emu_printf("could allocate "); 278 emu_printf(size); 279 } 280 281 return retval; 282 } 283 284 void emu_Free(void * pt) 285 { 286 free(pt); 287 } 288 289 290 291 292 293 int emu_ReadAnalogJoyX(int min, int max) 294 { 295 int val = analogRead(PIN_JOY2_A1X); 296 #if INVX 297 val = 4095 - val; 298 #endif 299 val = val-xRef; 300 val = ((val*140)/100); 301 if ( (val > -512) && (val < 512) ) val = 0; 302 val = val+2048; 303 return (val*(max-min))/4096; 304 } 305 306 int emu_ReadAnalogJoyY(int min, int max) 307 { 308 int val = analogRead(PIN_JOY2_A2Y); 309 #if INVY 310 val = 4095 - val; 311 #endif 312 val = val-yRef; 313 val = ((val*120)/100); 314 if ( (val > -512) && (val < 512) ) val = 0; 315 //val = (val*(max-min))/4096; 316 val = val+2048; 317 //return val+(max-min)/2; 318 return (val*(max-min))/4096; 319 } 320 321 322 static uint16_t readAnalogJoystick(void) 323 { 324 uint16_t joysval = 0; 325 326 int xReading = emu_ReadAnalogJoyX(0,256); 327 if (xReading > 128) joysval |= MASK_JOY2_LEFT; 328 else if (xReading < 128) joysval |= MASK_JOY2_RIGHT; 329 330 int yReading = emu_ReadAnalogJoyY(0,256); 331 if (yReading < 128) joysval |= MASK_JOY2_UP; 332 else if (yReading > 128) joysval |= MASK_JOY2_DOWN; 333 334 #ifdef PIN_JOY2_BTN 335 joysval |= (digitalRead(PIN_JOY2_BTN) == HIGH ? 0 : MASK_JOY2_BTN); 336 #endif 337 return (joysval); 338 } 339 340 341 int emu_SwapJoysticks(int statusOnly) { 342 if (!statusOnly) { 343 if (joySwapped) { 344 joySwapped = false; 345 } 346 else { 347 joySwapped = true; 348 } 349 } 350 return(joySwapped?1:0); 351 } 352 353 int emu_GetPad(void) 354 { 355 return(keypadval/*|((joySwapped?1:0)<<7)*/); 356 } 357 358 int emu_ReadKeys(void) 359 { 360 uint16_t retval; 361 uint16_t j1 = readAnalogJoystick(); 362 uint16_t j2 = 0; 363 364 // Second joystick 365 #if INVY 366 #ifdef PIN_JOY1_1 367 if ( digitalRead(PIN_JOY1_1) == LOW ) j2 |= MASK_JOY2_DOWN; 368 #endif 369 #ifdef PIN_JOY1_2 370 if ( digitalRead(PIN_JOY1_2) == LOW ) j2 |= MASK_JOY2_UP; 371 #endif 372 #else 373 #ifdef PIN_JOY1_1 374 if ( digitalRead(PIN_JOY1_1) == LOW ) j2 |= MASK_JOY2_UP; 375 #endif 376 #ifdef PIN_JOY1_2 377 if ( digitalRead(PIN_JOY1_2) == LOW ) j2 |= MASK_JOY2_DOWN; 378 #endif 379 #endif 380 #if INVX 381 #ifdef PIN_JOY1_3 382 if ( digitalRead(PIN_JOY1_3) == LOW ) j2 |= MASK_JOY2_LEFT; 383 #endif 384 #ifdef PIN_JOY1_4 385 if ( digitalRead(PIN_JOY1_4) == LOW ) j2 |= MASK_JOY2_RIGHT; 386 #endif 387 #else 388 #ifdef PIN_JOY1_3 389 if ( digitalRead(PIN_JOY1_3) == LOW ) j2 |= MASK_JOY2_RIGHT; 390 #endif 391 #ifdef PIN_JOY1_4 392 if ( digitalRead(PIN_JOY1_4) == LOW ) j2 |= MASK_JOY2_LEFT; 393 #endif 394 #endif 395 #ifdef PIN_JOY1_BTN 396 if ( digitalRead(PIN_JOY1_BTN) == LOW ) j2 |= MASK_JOY2_BTN; 397 #endif 398 if (joySwapped) { 399 retval = ((j1 << 8) | j2); 400 } 401 else { 402 retval = ((j2 << 8) | j1); 403 } 404 405 #ifdef PIN_KEY_USER1 406 if ( digitalRead(PIN_KEY_USER1) == LOW ) retval |= MASK_KEY_USER1; 407 #endif 408 #ifdef PIN_KEY_USER2 409 if ( digitalRead(PIN_KEY_USER2) == LOW ) retval |= MASK_KEY_USER2; 410 #endif 411 #ifdef PIN_KEY_USER3 412 if ( digitalRead(PIN_KEY_USER3) == LOW ) retval |= MASK_KEY_USER3; 413 #endif 414 #ifdef PIN_KEY_USER4 415 if ( digitalRead(PIN_KEY_USER4) == LOW ) retval |= MASK_KEY_USER4; 416 #endif 417 418 //Serial.println(retval,HEX); 419 420 if ( ((retval & (MASK_KEY_USER1+MASK_KEY_USER2)) == (MASK_KEY_USER1+MASK_KEY_USER2)) 421 || (retval & MASK_KEY_USER4 ) ) 422 { 423 // Reset procedure T3.X and T4.0 by Frank Boesing !! 424 #if defined(__IMXRT1052__) || defined(__IMXRT1062__) 425 uint32_t tmp = SNVS_LPCR; // save control register 426 427 SNVS_LPSR |= 1; 428 429 // disable alarm 430 SNVS_LPCR &= ~0x02; 431 while (SNVS_LPCR & 0x02); 432 433 __disable_irq(); 434 //get Time: 435 uint32_t lsb, msb; 436 do { 437 msb = SNVS_LPSRTCMR; 438 lsb = SNVS_LPSRTCLR; 439 } while ( (SNVS_LPSRTCLR != lsb) | (SNVS_LPSRTCMR != msb) ); 440 uint32_t secs = (msb << 17) | (lsb >> 15); 441 442 //set alarm 443 secs += 2; 444 SNVS_LPTAR = secs; 445 while (SNVS_LPTAR != secs); 446 447 SNVS_LPCR = tmp | 0x02; // restore control register and set alarm 448 while (!(SNVS_LPCR & 0x02)); 449 450 SNVS_LPCR |= (1 << 6); // turn off power 451 while (1) asm("wfi"); 452 #else 453 *(volatile uint32_t *)0xE000ED0C = 0x5FA0004; 454 while (true) { 455 ; 456 } 457 #endif 458 } 459 460 return (retval); 461 } 462 463 unsigned short emu_DebounceLocalKeys(void) 464 { 465 uint16_t bCurState = emu_ReadKeys(); 466 uint16_t bClick = bCurState & ~bLastState; 467 bLastState = bCurState; 468 469 return (bClick); 470 } 471 472 int emu_ReadI2CKeyboard(void) { 473 int retval=0; 474 #ifdef HAS_I2CKBD 475 if (i2cKeyboardPresent) { 476 byte msg[7]={0,0,0,0,0,0,0}; 477 Wire.requestFrom(8, 7); // request 7 bytes from slave device #8 478 int i = 0; 479 int hitindex=-1; 480 while (Wire.available() && (i<7) ) { // slave may send less than requested 481 byte b = Wire.read(); // receive a byte 482 if (b != 0xff) hitindex=i; 483 msg[i++] = b; 484 } 485 486 if (hitindex >=0 ) { 487 /* 488 Serial.println(msg[0], BIN); 489 Serial.println(msg[1], BIN); 490 Serial.println(msg[2], BIN); 491 Serial.println(msg[3], BIN); 492 Serial.println(msg[4], BIN); 493 Serial.println(msg[5], BIN); 494 Serial.println(msg[6], BIN); 495 */ 496 unsigned short match = (~msg[hitindex])&0x00FF | (hitindex<<8); 497 //Serial.println(match,HEX); 498 for (i=0; i<sizeof(i2ckeys); i++) { 499 if (match == i2ckeys[i]) { 500 //Serial.println((int)keys[i]); 501 return (keys[i]); 502 } 503 } 504 } 505 } 506 #endif 507 return(retval); 508 } 509 510 void emu_InitJoysticks(void) { 511 512 // Second Joystick 513 #ifdef PIN_JOY1_1 514 pinMode(PIN_JOY1_1, INPUT_PULLUP); 515 #endif 516 #ifdef PIN_JOY1_2 517 pinMode(PIN_JOY1_2, INPUT_PULLUP); 518 #endif 519 #ifdef PIN_JOY1_3 520 pinMode(PIN_JOY1_3, INPUT_PULLUP); 521 #endif 522 #ifdef PIN_JOY1_4 523 pinMode(PIN_JOY1_4, INPUT_PULLUP); 524 #endif 525 #ifdef PIN_JOY1_BTN 526 pinMode(PIN_JOY1_BTN, INPUT_PULLUP); 527 #endif 528 529 #ifdef PIN_KEY_USER1 530 pinMode(PIN_KEY_USER1, INPUT_PULLUP); 531 #endif 532 #ifdef PIN_KEY_USER2 533 pinMode(PIN_KEY_USER2, INPUT_PULLUP); 534 #endif 535 #ifdef PIN_KEY_USER3 536 pinMode(PIN_KEY_USER3, INPUT_PULLUP); 537 #endif 538 #ifdef PIN_KEY_USER4 539 pinMode(PIN_KEY_USER4, INPUT_PULLUP); 540 #endif 541 #ifdef PIN_JOY2_BTN 542 pinMode(PIN_JOY2_BTN, INPUT_PULLUP); 543 #endif 544 analogReadResolution(12); 545 xRef=0; yRef=0; 546 for (int i=0; i<10; i++) { 547 xRef += analogRead(PIN_JOY2_A1X); 548 yRef += analogRead(PIN_JOY2_A2Y); 549 delay(20); 550 } 551 552 #if INVX 553 xRef = 4095 -xRef/10; 554 #else 555 xRef /= 10; 556 #endif 557 #if INVY 558 yRef = 4095 -yRef/10; 559 #else 560 yRef /= 10; 561 #endif 562 } 563 564 565 566 static bool vkbKeepOn = false; 567 static bool vkbActive = false; 568 static bool vkeyRefresh=false; 569 static bool exitVkbd = false; 570 static uint8_t keyPressCount=0; 571 572 573 bool virtualkeyboardIsActive(void) { 574 return (vkbActive); 575 } 576 577 void toggleVirtualkeyboard(bool keepOn) { 578 579 if (keepOn) { 580 tft.drawSpriteNoDma(0,0,(uint16_t*)logo); 581 //prev_zt = 0; 582 vkbKeepOn = true; 583 vkbActive = true; 584 exitVkbd = false; 585 } 586 else { 587 vkbKeepOn = false; 588 if ( (vkbActive) /*|| (exitVkbd)*/ ) { 589 tft.fillScreenNoDma( RGBVAL16(0x00,0x00,0x00) ); 590 tft.startDMA(); 591 //prev_zt = 0; 592 vkbActive = false; 593 exitVkbd = false; 594 } 595 else { 596 tft.stopDMA(); 597 tft.drawSpriteNoDma(0,0,(uint16_t*)logo); 598 //prev_zt = 0; 599 vkbActive = true; 600 exitVkbd = false; 601 } 602 } 603 } 604 605 606 void handleVirtualkeyboard() { 607 int rx=0,ry=0,rw=0,rh=0; 608 609 if (keyPressCount == 0) { 610 keypadval = 0; 611 } else { 612 keyPressCount--; 613 } 614 615 if ( (!virtualkeyboardIsActive()) && (tft.isTouching()) && (!keyPressCount) ) { 616 toggleVirtualkeyboard(false); 617 return; 618 } 619 620 if ( ( (vkbKeepOn) || (virtualkeyboardIsActive()) ) ) { 621 char c = captureTouchZone(keysw, keys, &rx,&ry,&rw,&rh); 622 if (c) { 623 624 tft.drawRectNoDma( rx,ry,rw,rh, KEYBOARD_HIT_COLOR ); 625 if ( (c >=1) && (c <= ACTION_MAXKBDVAL) ) { 626 627 keypadval = c; 628 keyPressCount = 10; 629 delay(50); 630 vkeyRefresh = true; 631 exitVkbd = true; 632 } 633 else if (c == ACTION_EXITKBD) { 634 vkeyRefresh = true; 635 exitVkbd = true; 636 } 637 } 638 } 639 640 if (vkeyRefresh) { 641 vkeyRefresh = false; 642 tft.drawSpriteNoDma(0,0,(uint16_t*)logo, rx, ry, rw, rh); 643 } 644 645 if ( (exitVkbd) && (vkbActive) ) { 646 if (!vkbKeepOn) { 647 toggleVirtualkeyboard(false); 648 } 649 else { 650 toggleVirtualkeyboard(true); 651 } 652 } 653 } 654 655 int emu_setKeymap(int index) { 656 if (keyMap == 2) { 657 keyMap = 0; 658 keys = key_map1; 659 tft.drawText(0, 0, "N1 IN2 IN3 IN4 IN5 IN6 IN7 IN8 IN9 IN10I", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), true); 660 tft.drawText(0,16, "--- --- --- --- --- --- --- --- --- --- ", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), false); 661 tft.drawText(0,24, " q I w I e I r I t I y I u I i I o I p I", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0x80), true); 662 tft.drawText(0,40, "--- --- --- --- --- --- --- --- --- --- ", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0x80), false); 663 tft.drawText(0,48, " a I s I d I f I g I h I j I k I l IRTNI", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), true); 664 tft.drawText(0,64, "--- --- --- --- --- --- --- --- --- --- ", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), false); 665 tft.drawText(0,72, " z I x I c I v I b I n I m I , I ; ISPCI", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0x80), true); 666 tft.drawText(0,88, "--- --- --- --- --- --- --- --- --- --- ", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0x80), false); 667 delay(250); 668 } 669 else if (keyMap == 0) { 670 keyMap = 1; 671 keys = key_map2; 672 tft.drawText(0, 0, "F1 IF2 IF3 IF4 IF5 IF6 IF7 IF8 IF9 IF10I", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), true); 673 tft.drawText(0,16, "--- --- --- --- --- --- --- --- --- --- ", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), false); 674 tft.drawText(0,24, " q I w I e I r I t I y I u I i I o I p I", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0x80), true); 675 tft.drawText(0,40, "--- --- --- --- --- --- --- --- --- --- ", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0x80), false); 676 tft.drawText(0,48, " a I s I d I f I g I h I j I k I l IRTNI", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), true); 677 tft.drawText(0,64, "--- --- --- --- --- --- --- --- --- --- ", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), false); 678 tft.drawText(0,72, " z I x I c I v I b I n I m I , I ; ISPCI", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0x80), true); 679 tft.drawText(0,88, "--- --- --- --- --- --- --- --- --- --- ", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0x80), false); 680 delay(250); 681 } 682 else { 683 keyMap = 2; 684 keys = key_map3; 685 tft.drawText(0, 0, " 1 I 2 I 3 I 4 I 5 I 6 I 7 I 8 I 9 I 10I", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), true); 686 tft.drawText(0,16, "--- --- --- --- --- --- --- --- --- --- ", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), false); 687 tft.drawText(0,24, " q I w I e I r I t I y I u I i I o I p I", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0x80), true); 688 tft.drawText(0,40, "--- --- --- --- --- --- --- --- --- --- ", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0x80), false); 689 tft.drawText(0,48, " a I s I d I f I g I h I j I k I l IRTNI", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), true); 690 tft.drawText(0,64, "--- --- --- --- --- --- --- --- --- --- ", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), false); 691 tft.drawText(0,72, " z I x I c I v I b I n I m I , I ; ISPCI", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0x80), true); 692 tft.drawText(0,88, "--- --- --- --- --- --- --- --- --- --- ", RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0x80), false); 693 delay(250); 694 } 695 } 696 697 698 699 700 static int readNbFiles(void) { 701 int totalFiles = 0; 702 703 #ifdef USE_SDFS 704 DIR dir; 705 FILINFO entry; 706 f_opendir(&dir, romspath); 707 while ( (true) && (totalFiles<MAX_FILES) ) { 708 f_readdir(&dir, &entry); 709 if (!entry.fname[0]) { 710 // no more files 711 break; 712 } 713 char * filename = entry.fname; 714 Serial.println(filename); 715 if ( !(entry.fattrib & AM_DIR) ) { 716 strncpy(&files[totalFiles][0], filename, MAX_FILENAME_SIZE-1); 717 totalFiles++; 718 } 719 else { 720 if ( (strcmp(filename,".")) && (strcmp(filename,"..")) ) { 721 strncpy(&files[totalFiles][0], filename, MAX_FILENAME_SIZE-1); 722 totalFiles++; 723 } 724 } 725 } 726 f_closedir(&dir); 727 #else 728 File entry; 729 file = SD.open(romspath); 730 while ( (true) && (totalFiles<MAX_FILES) ) { 731 entry = file.openNextFile(); 732 if (! entry) { 733 // no more files 734 break; 735 } 736 #ifdef USE_SDFAT 737 char filename[MAX_FILENAME_SIZE]; 738 entry.getName(&filename[0], MAX_FILENAME_SIZE); 739 #else 740 char * filename = entry.name(); 741 #endif 742 Serial.println(filename); 743 if (!entry.isDirectory()) { 744 strncpy(&files[totalFiles][0], filename, MAX_FILENAME_SIZE-1); 745 totalFiles++; 746 } 747 else { 748 if ( (strcmp(filename,".")) && (strcmp(filename,"..")) ) { 749 strncpy(&files[totalFiles][0], filename, MAX_FILENAME_SIZE-1); 750 totalFiles++; 751 } 752 } 753 entry.close(); 754 } 755 file.close(); 756 #endif 757 return totalFiles; 758 } 759 760 761 762 void backgroundMenu(void) { 763 menuRedraw=true; 764 tft.fillScreenNoDma(RGBVAL16(0x00,0x00,0x00)); 765 tft.drawTextNoDma(0,0, TITLE, RGBVAL16(0x00,0xff,0xff), RGBVAL16(0x00,0x00,0xff), true); 766 tft.drawSpriteNoDma(MENU_VBAR_XOFFSET,MENU_VBAR_YOFFSET,(uint16_t*)bmpvbar); 767 #ifdef OLD_LAYOUT 768 tft.drawSpriteNoDma(MENU_TFT_XOFFSET,MENU_TFT_YOFFSET,(uint16_t*)bmptft); 769 tft.drawSpriteNoDma(MENU_VGA_XOFFSET,MENU_VGA_YOFFSET,(uint16_t*)bmpvga); 770 #endif 771 } 772 773 int handleMenu(uint16_t bClick) 774 { 775 int action = ACTION_NONE; 776 777 char newpath[80]; 778 strcpy(newpath, romspath); 779 strcat(newpath, "/"); 780 strcat(newpath, selection); 781 782 int rx=0,ry=0,rw=0,rh=0; 783 char c = 0; //captureTouchZone(menutouchareas, menutouchactions, &rx,&ry,&rw,&rh); 784 785 if ( (bClick & MASK_JOY2_BTN) || (c == MKEY_TFT) ) { 786 emu_printf(newpath); 787 #ifdef USE_SDFS 788 FILINFO entry; 789 f_stat(newpath, &entry); 790 if ( (entry.fattrib & AM_DIR) ) { 791 #else 792 File file = SD.open(newpath); 793 if (file.isDirectory()) { 794 #endif 795 strcpy(romspath,newpath); 796 curFile = 0; 797 nbFiles = readNbFiles(); 798 } 799 else { 800 action = ACTION_RUNTFT; 801 } 802 menuRedraw=true; 803 } 804 else if ( (bClick & MASK_KEY_USER1) || (c == MKEY_VGA) ) { 805 menuRedraw=true; 806 action = ACTION_RUNVGA; 807 } 808 else if ( (c >= MKEY_L1) && (c <= MKEY_L9) ) { 809 if ( (topFile+(int)c-1) <= (nbFiles-1) ) 810 { 811 curFile = topFile + (int)c -1; 812 menuRedraw=true; 813 //tft.drawRectNoDma( rx,ry,rw,rh, KEYBOARD_HIT_COLOR ); 814 } 815 } 816 else if (bClick & MASK_JOY2_UP) { 817 if (curFile!=0) { 818 menuRedraw=true; 819 curFile--; 820 } 821 } 822 else if ( (bClick & MASK_JOY2_RIGHT) || (bClick & MASK_JOY1_RIGHT) || (c == MKEY_UP) ) { 823 if ((curFile-9)>=0) { 824 menuRedraw=true; 825 curFile -= 9; 826 } else if (curFile!=0) { 827 menuRedraw=true; 828 curFile--; 829 } 830 } 831 else if (bClick & MASK_JOY2_DOWN) { 832 if ((curFile<(nbFiles-1)) && (nbFiles)) { 833 curFile++; 834 menuRedraw=true; 835 } 836 } 837 else if ( (bClick & MASK_JOY2_LEFT) || (bClick & MASK_JOY1_LEFT) || (c == MKEY_DOWN) ) { 838 if ((curFile<(nbFiles-9)) && (nbFiles)) { 839 curFile += 9; 840 menuRedraw=true; 841 } 842 else if ((curFile<(nbFiles-1)) && (nbFiles)) { 843 curFile++; 844 menuRedraw=true; 845 } 846 } 847 else if ( (bClick & MASK_KEY_USER2) || (c == MKEY_JOY) ) { 848 emu_SwapJoysticks(0); 849 menuRedraw=true; 850 } 851 852 if (menuRedraw && nbFiles) { 853 int fileIndex = 0; 854 tft.drawRectNoDma(MENU_FILE_XOFFSET,MENU_FILE_YOFFSET, MENU_FILE_W, MENU_FILE_H, MENU_FILE_BGCOLOR); 855 // if (curFile <= (MAX_MENULINES/2-1)) topFile=0; 856 // else topFile=curFile-(MAX_MENULINES/2); 857 if (curFile <= (MAX_MENULINES-1)) topFile=0; 858 else topFile=curFile-(MAX_MENULINES/2); 859 860 //Serial.print("curfile: "); 861 //Serial.println(curFile); 862 //Serial.print("topFile: "); 863 //Serial.println(topFile); 864 865 int i=0; 866 while (i<MAX_MENULINES) { 867 if (fileIndex>=nbFiles) { 868 // no more files 869 break; 870 } 871 char * filename = &files[fileIndex][0]; 872 if (fileIndex >= topFile) { 873 if ((i+topFile) < nbFiles ) { 874 if ((i+topFile)==curFile) { 875 tft.drawTextNoDma(MENU_FILE_XOFFSET,i*TEXT_HEIGHT+MENU_FILE_YOFFSET, filename, RGBVAL16(0xff,0xff,0x00), RGBVAL16(0xff,0x00,0x00), true); 876 strcpy(selection,filename); 877 } 878 else { 879 tft.drawTextNoDma(MENU_FILE_XOFFSET,i*TEXT_HEIGHT+MENU_FILE_YOFFSET, filename, 0xFFFF, 0x0000, true); 880 } 881 } 882 i++; 883 } 884 fileIndex++; 885 } 886 887 tft.drawSpriteNoDma(0,MENU_JOYS_YOFFSET,(uint16_t*)bmpjoy); 888 tft.drawTextNoDma(48,MENU_JOYS_YOFFSET+8, (emu_SwapJoysticks(1)?(char*)"SWAP=1":(char*)"SWAP=0"), RGBVAL16(0x00,0xff,0xff), RGBVAL16(0xff,0x00,0x00), false); 889 menuRedraw=false; 890 } 891 892 return (action); 893 } 894 895 bool menuActive(void) 896 { 897 return (menuOn); 898 } 899 900 void toggleMenu(bool on) { 901 if (on) { 902 callibrationOn=false; 903 menuOn=true; 904 backgroundMenu(); 905 } else { 906 menuOn = false; 907 } 908 } 909 910 char * menuSelection(void) 911 { 912 return (selection); 913 } 914 915 916 917 918 static void callibrationInit(void) 919 { 920 callibrationOn=true; 921 menuOn=false; 922 callibrationStep = 0; 923 calMinX=0,calMinY=0,calMaxX=0,calMaxY=0; 924 tft.fillScreenNoDma(RGBVAL16(0xff,0xff,0xff)); 925 tft.drawTextNoDma(0,100, " Callibration process:", RGBVAL16(0x00,0x00,0x00), RGBVAL16(0xff,0xff,0xff), true); 926 tft.drawTextNoDma(0,116, " Hit the red cross at each corner", RGBVAL16(0x00,0x00,0x00), RGBVAL16(0xff,0xff,0xff), true); 927 tft.drawTextNoDma(0,0, "+", RGBVAL16(0xff,0x00,0x00), RGBVAL16(0xff,0xff,0xff), true); 928 prev_zt = 1; 929 } 930 931 932 static void readCallibration(void) 933 { 934 char fileBuffer[64]; 935 936 #ifdef USE_SDFS 937 FIL file; 938 int retval; 939 if( !(f_open(&file, CALIBRATION_FILE, FA_READ)) ) { 940 if( !(f_read (&file, fileBuffer, 64, &retval)) ) { 941 if (retval == 64) { 942 sscanf(fileBuffer,"%d %d %d %d", &calMinX,&calMinY,&calMaxX,&calMaxY); 943 } 944 } 945 f_close(&file); 946 } 947 #else 948 File file = SD.open(CALIBRATION_FILE, O_READ); 949 if (file) { 950 if ( file.read(fileBuffer, 64) ) { 951 sscanf(fileBuffer,"%d %d %d %d", &calMinX,&calMinY,&calMaxX,&calMaxY); 952 } 953 file.close(); 954 Serial.println("Current callibration params:"); 955 Serial.println(calMinX); 956 Serial.println(calMinY); 957 Serial.println(calMaxX); 958 Serial.println(calMaxY); 959 } 960 #endif 961 else { 962 Serial.println("Callibration read error"); 963 } 964 tft.callibrateTouch(calMinX,calMinY,calMaxX,calMaxY); 965 } 966 967 static void writeCallibration(void) 968 { 969 tft.callibrateTouch(calMinX,calMinY,calMaxX,calMaxY); 970 971 #ifdef USE_SDFS 972 FIL file; 973 int retval; 974 if( !(f_open(&file, CALIBRATION_FILE, FA_WRITE)) ) { 975 //if( !(f_read (&file, fileBuffer, 64, &retval)) ) { 976 // if (retval == 64) { 977 // sscanf(fileBuffer,"%d %d %d %d", &calMinX,&calMinY,&calMaxX,&calMaxY); 978 // } 979 //} 980 f_close(&file); 981 } 982 #else 983 File file = SD.open(CALIBRATION_FILE, O_WRITE | O_CREAT | O_TRUNC); 984 if (file) { 985 file.print(calMinX); 986 file.print(" "); 987 file.print(calMinY); 988 file.print(" "); 989 file.print(calMaxX); 990 file.print(" "); 991 file.println(calMaxY); 992 file.close(); 993 } 994 #endif 995 else { 996 Serial.println("Callibration write error"); 997 } 998 } 999 1000 1001 bool callibrationActive(void) 1002 { 1003 return (callibrationOn); 1004 } 1005 1006 1007 1008 int handleCallibration(uint16_t bClick) { 1009 uint16_t xt=0; 1010 uint16_t yt=0; 1011 uint16_t zt=0; 1012 if (tft.isTouching()) { 1013 if (prev_zt == 0) { 1014 prev_zt = 1; 1015 tft.readRaw(&xt,&yt,&zt); 1016 if (zt < 1000) { 1017 return 0; 1018 } 1019 switch (callibrationStep) 1020 { 1021 case 0: 1022 callibrationStep++; 1023 tft.drawTextNoDma(0,0, " ", RGBVAL16(0xff,0xff,0xff), RGBVAL16(0xff,0xff,0xff), true); 1024 tft.drawTextNoDma(TFT_REALWIDTH-8,0, "+", RGBVAL16(0xff,0x00,0x00), RGBVAL16(0xff,0xff,0xff), true); 1025 calMinX += xt; 1026 calMinY += yt; 1027 break; 1028 case 1: 1029 callibrationStep++; 1030 tft.drawTextNoDma(TFT_REALWIDTH-8,0, " ", RGBVAL16(0xff,0xff,0xff), RGBVAL16(0xff,0xff,0xff), true); 1031 tft.drawTextNoDma(TFT_REALWIDTH-8,TFT_REALHEIGHT-16, "+", RGBVAL16(0xff,0x00,0x00), RGBVAL16(0xff,0xff,0xff), true); 1032 calMaxX += xt; 1033 calMinY += yt; 1034 break; 1035 case 2: 1036 callibrationStep++; 1037 tft.drawTextNoDma(TFT_REALWIDTH-8,TFT_REALHEIGHT-16, " ", RGBVAL16(0xff,0xff,0xff), RGBVAL16(0xff,0xff,0xff), true); 1038 tft.drawTextNoDma(0,TFT_REALHEIGHT-16, "+", RGBVAL16(0xff,0x00,0x00), RGBVAL16(0xff,0xff,0xff), true); 1039 calMaxX += xt; 1040 calMaxY += yt; 1041 break; 1042 case 3: 1043 tft.fillScreenNoDma(RGBVAL16(0xff,0xff,0xff)); 1044 tft.drawTextNoDma(0,100, " Callibration done!", RGBVAL16(0x00,0x00,0x00), RGBVAL16(0xff,0xff,0xff), true); 1045 tft.drawTextNoDma(0,116, " (Click center to exit)", RGBVAL16(0xff,0x00,0x00), RGBVAL16(0xff,0xff,0xff), true); 1046 callibrationStep++; 1047 calMinX += xt; 1048 calMaxY += yt; 1049 break; 1050 case 4: 1051 //Serial.println(xt); 1052 //Serial.println(yt); 1053 if ( (xt > (TFT_REALWIDTH/4)) && (xt < (TFT_REALWIDTH*3)/4) 1054 && (yt > (TFT_REALHEIGHT/4)) && (yt < (TFT_REALHEIGHT*3)/4) ) { 1055 calMinX /= 2; 1056 calMinY /= 2; 1057 calMaxX /= 2; 1058 calMaxY /= 2; 1059 writeCallibration(); 1060 toggleMenu(true); 1061 } 1062 else { 1063 callibrationInit(); 1064 } 1065 break; 1066 1067 } 1068 delay(100); 1069 } 1070 } 1071 else { 1072 prev_zt = 0; 1073 } 1074 } 1075 1076 1077 1078 1079 1080 int emu_FileOpen(char * filename) 1081 { 1082 int retval = 0; 1083 1084 char filepath[80]; 1085 strcpy(filepath, romspath); 1086 strcat(filepath, "/"); 1087 strcat(filepath, filename); 1088 emu_printf("FileOpen..."); 1089 emu_printf(filepath); 1090 #ifdef USE_SDFS 1091 if( !(f_open(&file, filepath, FA_READ)) ) { 1092 #else 1093 if ((file = SD.open(filepath, O_READ))) { 1094 #endif 1095 retval = 1; 1096 } 1097 else { 1098 emu_printf("FileOpen failed"); 1099 } 1100 return (retval); 1101 } 1102 1103 int emu_FileRead(char * buf, int size) 1104 { 1105 unsigned char buffer[256]; 1106 1107 int remaining = size; 1108 int byteread = 0; 1109 int retval=0; 1110 if (size < 256) { 1111 #ifdef USE_SDFS 1112 if( !(f_read (&file, buffer, size, &retval)) ) 1113 #else 1114 retval = file.read(buffer, size); 1115 #endif 1116 if (retval>0) { 1117 memcpy(buf,buffer,retval); 1118 byteread += retval; 1119 } 1120 } 1121 else { 1122 while (remaining>0) { 1123 #ifdef USE_SDFS 1124 if( !(f_read (&file, buffer, 256, &retval)) ) 1125 //f_read (&file, buffer, 256, &retval); 1126 #else 1127 retval = file.read(buffer, 256); 1128 #endif 1129 if (retval>0) { 1130 //emu_printi(retval); 1131 memcpy(buf,buffer,retval); 1132 buf += retval; 1133 byteread += retval; 1134 remaining -= retval; 1135 } 1136 else { 1137 break; 1138 } 1139 } 1140 } 1141 1142 return byteread; 1143 } 1144 1145 unsigned char emu_FileGetc(void) { 1146 unsigned char c; 1147 #ifdef USE_SDFS 1148 int retval=0; 1149 if( !(f_read (&file, &c, 1, &retval)) ) 1150 #else 1151 int retval = file.read(&c, 1); 1152 #endif 1153 if (retval != 1) { 1154 emu_printf("emu_FileGetc failed"); 1155 } 1156 return c; 1157 } 1158 1159 1160 void emu_FileClose(void) 1161 { 1162 #ifdef USE_SDFS 1163 f_close(&file); 1164 #else 1165 file.close(); 1166 #endif 1167 } 1168 1169 int emu_FileSize(char * filename) 1170 { 1171 int filesize=0; 1172 char filepath[80]; 1173 strcpy(filepath, romspath); 1174 strcat(filepath, "/"); 1175 strcat(filepath, filename); 1176 emu_printf("FileSize..."); 1177 emu_printf(filepath); 1178 #ifdef USE_SDFS 1179 FILINFO entry; 1180 f_stat(filepath, &entry); 1181 filesize = entry.fsize; 1182 #else 1183 if ((file = SD.open(filepath, O_READ))) 1184 { 1185 emu_printf("filesize is..."); 1186 filesize = file.size(); 1187 emu_printf(filesize); 1188 file.close(); 1189 } 1190 #endif 1191 1192 return(filesize); 1193 } 1194 1195 int emu_FileSeek(int seek) 1196 { 1197 #ifdef USE_SDFS 1198 f_lseek(&file, seek); 1199 #else 1200 file.seek(seek); 1201 #endif 1202 return (seek); 1203 } 1204 1205 int emu_FileTell(void) 1206 { 1207 #ifdef USE_SDFS 1208 return (f_tell(&file)); 1209 #else 1210 return (50); 1211 #endif 1212 } 1213 1214 1215 int emu_LoadFile(char * filename, char * buf, int size) 1216 { 1217 int filesize = 0; 1218 1219 char filepath[80]; 1220 strcpy(filepath, romspath); 1221 strcat(filepath, "/"); 1222 strcat(filepath, filename); 1223 emu_printf("LoadFile..."); 1224 emu_printf(filepath); 1225 #ifdef USE_SDFS 1226 if( !(f_open(&file, filepath, FA_READ)) ) { 1227 filesize = f_size(&file); 1228 emu_printf(filesize); 1229 if (size >= filesize) 1230 { 1231 int retval=0; 1232 if( (f_read (&file, buf, filesize, &retval)) ) { 1233 emu_printf("File read failed"); 1234 } 1235 } 1236 f_close(&file); 1237 } 1238 #else 1239 if ((file = SD.open(filepath, O_READ))) 1240 { 1241 filesize = file.size(); 1242 emu_printf(filesize); 1243 1244 if (size >= filesize) 1245 { 1246 if (emu_FileRead(buf, filesize) != filesize) 1247 { 1248 emu_printf("File read failed"); 1249 } 1250 } 1251 file.close(); 1252 } 1253 #endif 1254 1255 return(filesize); 1256 } 1257 1258 int emu_LoadFileSeek(char * filename, char * buf, int size, int seek) 1259 { 1260 int filesize = 0; 1261 1262 char filepath[80]; 1263 strcpy(filepath, romspath); 1264 strcat(filepath, "/"); 1265 strcat(filepath, filename); 1266 emu_printf("LoadFileSeek..."); 1267 emu_printf(filepath); 1268 #ifdef USE_SDFS 1269 if( !(f_open(&file, filepath, FA_READ)) ) { 1270 f_lseek(&file, seek); 1271 emu_printf(size); 1272 if (size >= filesize) 1273 { 1274 int retval=0; 1275 if( (!f_read (&file, buf, size, &retval)) ) 1276 if (retval != size) 1277 { 1278 emu_printf("File read failed"); 1279 } 1280 } 1281 f_close(&file); 1282 } 1283 #else 1284 if ((file = SD.open(filepath, O_READ))) 1285 { 1286 file.seek(seek); 1287 emu_printf(size); 1288 if (file.read(buf, size) != size) { 1289 emu_printf("File read failed"); 1290 } 1291 file.close(); 1292 } 1293 #endif 1294 1295 return(filesize); 1296 } 1297 1298 const uint32_t FILE_SIZE_MB = 8; 1299 const uint32_t FILE_SIZE = 1000000UL*FILE_SIZE_MB; 1300 #ifdef USE_SDFS 1301 static FIL tempfile; 1302 #else 1303 static File tempfile; 1304 #endif 1305 1306 void emu_FileTempInit(void) 1307 { 1308 #ifdef USE_SDFS 1309 if( (f_open(&tempfile, SDFSDEV "/bench.dat", FA_READ| FA_WRITE )) ) { 1310 #else 1311 #ifdef USE_SDFAT 1312 if (!tempfile.open("/bench.dat", O_RDWR /*| O_CREAT | O_TRUNC*/)) { 1313 #else 1314 if ((tempfile = SD.open("/bench.dat", O_RDWR))) { 1315 #endif 1316 #endif 1317 Serial.println("psram open failed"); 1318 } 1319 /* 1320 else { 1321 uint8_t buf[256]; 1322 Serial.println("psram creating"); 1323 file = SD.open("/bench.dat", O_RDWR | O_CREAT | O_TRUNC); 1324 if (file) { 1325 Serial.println("psram opened"); 1326 file.truncate(0); 1327 1328 if (!file.preAllocate(FILE_SIZE)) { 1329 Serial.println("allocate failed"); 1330 } 1331 for(int i=0;i<FILE_SIZE/256;i++){ 1332 file.write(buf, 256); 1333 Serial.println(i); 1334 1335 } 1336 Serial.println("psram created"); 1337 } 1338 1339 //file.close(); 1340 } 1341 */ 1342 #ifdef USE_SDFS 1343 FILINFO entry; 1344 f_stat(SDFSDEV "/bench.dat", &entry); 1345 int fs=entry.fsize; 1346 #else 1347 int fs=tempfile.size(); 1348 #endif 1349 Serial.print("psram size is "); 1350 Serial.println(fs); 1351 } 1352 1353 void emu_FileTempRead(int addr, unsigned char * val, int n) 1354 { 1355 #ifdef USE_SDFS 1356 f_lseek(&file, addr); 1357 int retval=0; 1358 f_read (&file, val, n, &retval); 1359 #else 1360 tempfile.seek(addr); 1361 tempfile.read(val, n); 1362 #endif 1363 } 1364 1365 void emu_FileTempWrite(int addr, unsigned char val) 1366 { 1367 uint8_t v=val; 1368 #ifdef USE_SDFS 1369 f_lseek(&tempfile, addr); 1370 int retval=0; 1371 f_write (&tempfile, &v, 1, &retval); 1372 #else 1373 tempfile.seek(addr); 1374 tempfile.write(&v, 1); 1375 #endif 1376 } 1377 1378 1379 void emu_init(void) 1380 { 1381 Serial.begin(115200); 1382 1383 #ifdef USE_SDFS 1384 strcpy(romspath,SDFSDEV); 1385 strcat(romspath,ROMSDIR); 1386 FRESULT rc; 1387 if((rc = f_mount (&fatfs, romspath, 1))) { 1388 emu_printf("Fail mounting SDFS"); 1389 } 1390 else { 1391 rc = f_chdrive(ROMSDIR); 1392 } 1393 #else 1394 #ifdef USE_SDFAT 1395 while (!SD.begin(SD_CONFIG)) 1396 #else 1397 while (!SD.begin(SD_CS)) 1398 #endif 1399 { 1400 Serial.println("SD begin failed, retrying..."); 1401 delay(1000); 1402 } 1403 strcpy(romspath,ROMSDIR); 1404 #endif 1405 1406 nbFiles = readNbFiles(); 1407 1408 Serial.print("SD initialized, files found: "); 1409 Serial.println(nbFiles); 1410 1411 1412 emu_InitJoysticks(); 1413 #ifdef SWAP_JOYSTICK 1414 joySwapped = true; 1415 #else 1416 joySwapped = false; 1417 #endif 1418 1419 readCallibration(); 1420 1421 if ((tft.isTouching()) || (emu_ReadKeys() & MASK_JOY2_BTN) ) { 1422 callibrationInit(); 1423 } 1424 else 1425 { 1426 toggleMenu(true); 1427 } 1428 1429 #ifdef HAS_I2CKBD 1430 byte msg[7]={0,0,0,0,0,0,0}; 1431 Wire.begin(); // join i2c bus SDA2/SCL2 1432 Wire.requestFrom(8, 7); // request 7 bytes from slave device #8 1433 int i = 0; 1434 while (Wire.available() && (i<7) ) { // slave may send less than requested 1435 byte b = Wire.read(); // receive a byte 1436 msg[i++] = b; 1437 } 1438 /* 1439 Serial.println(msg[0], BIN); 1440 Serial.println(msg[1], BIN); 1441 Serial.println(msg[2], BIN); 1442 Serial.println(msg[3], BIN); 1443 Serial.println(msg[4], BIN); 1444 Serial.println(msg[5], BIN); 1445 Serial.println(msg[6], BIN); 1446 */ 1447 if ( (msg[0] == 0xff) && (msg[1] == 0xff) && 1448 (msg[2] == 0xff) && (msg[3] == 0xff) && 1449 (msg[4] == 0xff) && (msg[5] == 0xff) && (msg[6] == 0xff)) { 1450 i2cKeyboardPresent = true; 1451 Serial.println("i2C keyboard found"); 1452 } 1453 #endif 1454 1455 keys = key_map3; 1456 keyMap = 2; 1457 } 1458