The porting of the NESBot Play the 'Tool Assisted Speedrun' videos on the real machine(NES). original (with Arduino): http://www.instructables.com/id/NESBot-Arduino-Powered-Robot-beating-Super-Mario-/ Almost same as the original, it need generated Key-input data by emulator with Lua script. See the original instructables' documents to know how to generate data file. BOM: mbed x1 NES x1 NES controller x1 4021(shift registor) x1
main.cpp
00001 #include "mbed.h" 00002 00003 // - The porting of the NESBot 00004 // original : http://www.instructables.com/id/NESBot-Arduino-Powered-Robot-beating-Super-Mario-/ 00005 // 00006 // ported by Kaoru Shoji : http://mbed.org/users/kshoji 00007 // 00008 // - Connections: 00009 // a NES, a mbed and a 4021 (shift register) needed. 00010 // 00011 // for example) AV-FAMICOM(JPY) connector pinout 00012 // 1 LATCH (PL, P/S) -> mbed's 9 pin 00013 // 2 CLOCK -> 4021's 10 pin 00014 // 3 VCC -> 4021's 16 pin 00015 // 4 GND -> mbed's GND & 4021's 8 pin 00016 // 5 DATA -> 4021's 3 pin 00017 // 00018 // - Note: 00019 // The mbed's VCC must be supplied from USB cable. 00020 // If mbed's VCC is supplied from NES VCC, the LATCH signal detection may be failed. 00021 // 00022 // - How to use: 00023 // 0. Prepare the replay data with FCEUX and Lua script. (Lua script can be downloaded from instructables). 00024 // The data file needs to be placed into mbed's LocalFileSystem(on the root directory). 00025 // 1. NES power turn off. 00026 // 2. connect mbed to NES, and USB power. 00027 // 3. NES power turn on. 00028 00029 InterruptIn latchInterrupt(p9); // LATCH signal in 00030 00031 DigitalOut R(p10); // -> 4021's p1(7) 00032 DigitalOut L(p11); // -> 4021's p2(6) 00033 DigitalOut D(p12); // -> 4021's p3(5) 00034 DigitalOut U(p13); // -> 4021's p4(4) 00035 DigitalOut T(p14); // -> 4021's p5(13) 00036 DigitalOut S(p15); // -> 4021's p6(14) 00037 DigitalOut B(p16); // -> 4021's p7(15) 00038 DigitalOut A(p17); // -> 4021's p8(1) 00039 00040 // status LEDs 00041 DigitalOut led1(LED1); 00042 DigitalOut led2(LED2); 00043 DigitalOut led3(LED3); 00044 DigitalOut led4(LED4); 00045 00046 LocalFileSystem local("mbed"); 00047 00048 // Large buffer may cause time rag when file loading. 00049 #define BUFFER_LENGTH (128) 00050 00051 unsigned char controllerData[BUFFER_LENGTH]; 00052 int controllerDataPosition = 0; 00053 00054 FILE *fp; 00055 long fileLength = 0; 00056 long filePosition = 0; 00057 00058 volatile bool finished = false; 00059 00060 void writeButtons() { 00061 unsigned char state = ~controllerData[controllerDataPosition]; 00062 00063 // output to shift register 00064 R = state & 0x80; 00065 L = state & 0x40; 00066 D = state & 0x20; 00067 U = state & 0x10; 00068 T = state & 0x08; 00069 S = state & 0x04; 00070 B = state & 0x02; 00071 A = state & 0x01; 00072 } 00073 00074 void showLEDs() { 00075 led1 = !U | !D; 00076 led2 = !L | !R; 00077 led3 = !A; 00078 led4 = !B; 00079 } 00080 00081 void trigger() { 00082 // when P/S Control signal falled(Serial mode) 00083 // read the controller state 00084 writeButtons(); 00085 showLEDs(); 00086 00087 filePosition++; 00088 if (filePosition >= fileLength) { 00089 latchInterrupt.fall(0); 00090 finished = true; 00091 return; 00092 } 00093 00094 controllerDataPosition++; 00095 if (controllerDataPosition >= BUFFER_LENGTH) { 00096 fread(controllerData, 1, BUFFER_LENGTH, fp); 00097 controllerDataPosition = 0; 00098 } 00099 } 00100 00101 int main() { 00102 // TODO replace your filename 00103 fp = fopen("/mbed/tas.txt", "rb"); 00104 controllerDataPosition = 0; 00105 00106 fseek(fp, 0L, SEEK_END); 00107 fileLength = ftell(fp); 00108 fseek(fp, 0L, SEEK_SET); 00109 00110 fread(controllerData, 1, BUFFER_LENGTH, fp); 00111 writeButtons(); 00112 00113 latchInterrupt.mode(PullNone); 00114 latchInterrupt.fall(&trigger); 00115 00116 while(!finished); 00117 fclose(fp); 00118 }
Generated on Thu Jul 21 2022 13:40:38 by 1.7.2