Ryan Savitski
/
LEDsnake
LED screen snake as an example of 48x48 panelspace working.
Embed:
(wiki syntax)
Show/hide line numbers
main.cpp
00001 #include "mbed.h" 00002 #include "ledScreen.h" 00003 00004 // screen instance 00005 ledScreen screen; 00006 00007 // controller 00008 AnalogIn xJoy(p20); 00009 AnalogIn yJoy(p19); 00010 DigitalIn Abutton(p22); 00011 DigitalIn Bbutton(p21); 00012 00013 //snake 00014 struct snakeBitPos 00015 { 00016 signed char x; 00017 signed char y; 00018 }; 00019 00020 // sin lookup table and related functions 00021 unsigned char sinlut[256]; 00022 00023 void initSinLut() { 00024 for (int i=0; i<256; i++) 00025 sinlut[i] = cos((float)i / 256.0 * (3.14159265 * 2))*127 + 128; 00026 } 00027 00028 inline unsigned char lut_sin(int x) { 00029 00030 return (x>0)?sinlut[x%256]:sinlut[(-x)%256]; 00031 } 00032 00033 00034 // Example frame makes: 00035 00036 00037 //rainbow 00038 void makeFrame1(unsigned char* data) { 00039 00040 static int time=0; 00041 time++; 00042 00043 // override data with a intensity gradient test pattern 00044 for (int x=0; x<3*16; x++) { 00045 for (int y=0; y<48; y++) { 00046 00047 int i = (x + y*(16*3)) * 3; // figure out the memory location 00048 00049 data[i] = lut_sin((x+y)*255/48+(time/2)%256); //(sin((float)(x+time)/15.0)+1.0)*128 ; // red 00050 data[i+1] = lut_sin(((x+y)*255/48+(time/2)+ 85)%256); //(sin((float)(x+time)/15.0)+1.0)*128 ; // red 00051 data[i+2] = lut_sin(((x+y)*255/48+(time/2)+170)%256); //(sin((float)(x+time)/15.0)+1.0)*128 ; // red 00052 } 00053 } 00054 00055 } 00056 00057 //cool lines 00058 void makeFrame2(unsigned char* data) { 00059 00060 static int time=0; 00061 time++; 00062 00063 // override data with a intensity gradient test pattern 00064 for (int x=0; x<3*16; x++) { 00065 for (int y=0; y<16; y++) { 00066 00067 int i = (x + y*(16*3)) * 3; // figure out the memory location 00068 00069 data[i] = lut_sin(x*255/48+(time)%256 + y*16); //(sin((float)(x+time)/15.0)+1.0)*128 ; // red 00070 data[i+1] = lut_sin(x*255/48+(time)%256 + y*16 + 85); //(sin((float)(x+time)/15.0)+1.0)*128 ; // red 00071 data[i+2] = lut_sin(x*255/48+(time)%256 + y*16 + 170); //(sin((float)(x+time)/15.0)+1.0)*128 ; // red 00072 } 00073 } 00074 00075 } 00076 00077 // static gradients 00078 void makeFrame3(unsigned char* data) { 00079 00080 static int time=0; 00081 time++; 00082 00083 // override data with a intensity gradient test pattern 00084 for (int x=0; x<3*16; x++) { 00085 for (int y=0; y<16; y++) { 00086 00087 int i = (x + y*(16*3)) * 3; // figure out the memory location 00088 00089 data[i] = x*256/48; //(sin((float)(x+time)/15.0)+1.0)*128 ; // red 00090 data[i+1] = 0; // green 00091 data[i+2] = y*256/16; //(i/3)%256 ; // blue 00092 } 00093 } 00094 00095 } 00096 00097 void makeEmptyFrame(unsigned char* data) 00098 { 00099 for (int x=0; x<3*16; x++) { 00100 for (int y=0; y<3*16; y++) { 00101 00102 int i = (x + y*(16*3)) * 3; // figure out the memory location 00103 00104 data[i] = 0; 00105 data[i+1] = 0; 00106 data[i+2] = 0; 00107 } 00108 } 00109 00110 } 00111 00112 void stepSnake(unsigned char* data) 00113 { 00114 static snakeBitPos dotLoc; // going to be the dot 00115 static unsigned short length=2; 00116 static unsigned char dir; 00117 static snakeBitPos snakeArr[100]; 00118 00119 static bool firstCall=true; 00120 if (firstCall) { snakeArr[0].x=20; snakeArr[0].y=20; firstCall=false; dotLoc.x=rand()%48; dotLoc.y=rand()%48; } 00121 static bool gameover=false; 00122 static short speed_n = 50; 00123 00124 if (!gameover) 00125 { 00126 00127 static unsigned short time=0; 00128 time++; 00129 time = time%(speed_n/2); // smaller constant = higher speed 00130 00131 00132 // updating direction on every invocation 00133 float xReading = xJoy.read(); 00134 float yReading = yJoy.read(); 00135 00136 if (xReading > 0.9 && dir != 1) 00137 {dir = 0; } 00138 else if(xReading < 0.3 && dir != 0) 00139 {dir = 1; } 00140 else if(yReading > 0.9 && dir != 3) 00141 {dir = 2; } 00142 else if(yReading < 0.3 && dir != 2) 00143 {dir = 3; } 00144 00145 00146 // moving the snake forward 00147 if (time == 0) 00148 { 00149 for (int j=length; j>0; j--) 00150 { 00151 snakeArr[j]=snakeArr[j-1]; 00152 } 00153 switch(dir) 00154 { 00155 case(0): 00156 (snakeArr[0]).x++; 00157 break; 00158 case(1): 00159 (snakeArr[0]).x--; 00160 break; 00161 case(2): 00162 (snakeArr[0]).y++; 00163 break; 00164 case(3): 00165 (snakeArr[0]).y--; 00166 break; 00167 } 00168 00169 // wrapping 00170 if (snakeArr[0].x==-1) snakeArr[0].x=47; 00171 if (snakeArr[0].x==48) snakeArr[0].x=0; 00172 if (snakeArr[0].y==48) snakeArr[0].y=0; 00173 if (snakeArr[0].y==-1) snakeArr[0].y=47; 00174 00175 if (snakeArr[0].y==dotLoc.y && snakeArr[0].x==dotLoc.x) 00176 { 00177 dotLoc.x = rand()%48; 00178 dotLoc.y = rand()%48; 00179 length++; 00180 speed_n--; if (speed_n<2) speed_n=2; 00181 } 00182 00183 // outputting 00184 int i=0; 00185 // killing own tail (no need to zero whole screen) 00186 i = (snakeArr[length].x+(snakeArr[length].y)*48)*3; 00187 data[i] = 0; 00188 data[i+2] = 0; 00189 00190 // new head alone (no need for looping) 00191 i = (snakeArr[0].x+(snakeArr[0].y)*48)*3; 00192 00193 // if hitting self, game over 00194 if (data[i]==255) {data[i+1] = 255; gameover=true;} 00195 00196 data[i] = 255; 00197 data[i+2] = 127; 00198 00199 data[(dotLoc.x+dotLoc.y*48)*3 +2] = 255; 00200 } 00201 } 00202 } 00203 00204 00205 void makeFrame33(unsigned char* data) { 00206 00207 static int time=0; 00208 time++; 00209 00210 for (int x=0; x<3*16; x++) { 00211 for (int y=0; y<48; y++) { 00212 00213 int i = (x + y*(16*3)) * 3; // figure out the memory location 00214 00215 data[i] = x*256/48; //(sin((float)(x+time)/15.0)+1.0)*128 ; // red 00216 data[i+1] = 0; // green 00217 data[i+2] = y*256/48; //(i/3)%256 ; // blue 00218 } 00219 } 00220 } 00221 00222 int main() 00223 { 00224 00225 // framebuffer on client side 00226 unsigned char imageSource[256*3*3*3] = { 0 }; 00227 00228 // prepare sin lookup table (optional) 00229 initSinLut(); 00230 00231 // start the screen output, which will keep outputting the frames that are in its internal buffer (updated via .transformFrame) 00232 screen.start(); 00233 00234 makeEmptyFrame(imageSource); 00235 00236 while (1) { 00237 00238 stepSnake(imageSource); // prepare framebuffer with current frame 00239 screen.transformFrame(imageSource); // write framebuffer to output framebuffer 00240 wait_ms(0.5); // slow down the framerate (optional) 00241 } 00242 00243 }
Generated on Tue Jul 19 2022 19:39:03 by 1.7.2