Example drawing mandelbrot on the RA8875 with touch to zoom in or out. Touch and hold > 4s to zoom out, touch to zoom in.
Saw the nice mandelbrot demo from Bob Stone and leverage it to use this library.
main.cpp@1:14319ec53540, 2015-01-15 (annotated)
- Committer:
- WiredHome
- Date:
- Thu Jan 15 12:37:13 2015 +0000
- Revision:
- 1:14319ec53540
- Parent:
- 0:702ce703348d
- Child:
- 2:feda27c3a523
Clean up dead code
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
WiredHome | 0:702ce703348d | 1 | #include "mbed.h" |
WiredHome | 1:14319ec53540 | 2 | #include "RA8875.h" |
WiredHome | 1:14319ec53540 | 3 | |
WiredHome | 1:14319ec53540 | 4 | LocalFileSystem local("local"); //file system |
WiredHome | 1:14319ec53540 | 5 | Serial pc(USBTX, USBRX); |
WiredHome | 1:14319ec53540 | 6 | RA8875 lcd(p5, p6, p7, p12, NC, "tft"); // MOSI, MISO, SCK, /ChipSelect, /reset, name |
WiredHome | 1:14319ec53540 | 7 | |
WiredHome | 1:14319ec53540 | 8 | uint16_t width, height; |
WiredHome | 0:702ce703348d | 9 | |
WiredHome | 1:14319ec53540 | 10 | int GetScreenCapture(void) |
WiredHome | 1:14319ec53540 | 11 | { |
WiredHome | 1:14319ec53540 | 12 | char fqfn[50]; |
WiredHome | 1:14319ec53540 | 13 | int i = 0; |
WiredHome | 1:14319ec53540 | 14 | |
WiredHome | 1:14319ec53540 | 15 | pc.printf("Screen Capture... "); |
WiredHome | 1:14319ec53540 | 16 | for (i=1; i< 100; i++) { |
WiredHome | 1:14319ec53540 | 17 | snprintf(fqfn, sizeof(fqfn), "/local/Screen%02d.bmp", i); |
WiredHome | 1:14319ec53540 | 18 | FILE * fh = fopen(fqfn, "rb"); |
WiredHome | 1:14319ec53540 | 19 | if (!fh) { |
WiredHome | 1:14319ec53540 | 20 | lcd.PrintScreen(0,0,480,272,fqfn); |
WiredHome | 1:14319ec53540 | 21 | pc.printf(" as /local/Screen%02d.bmp\r\n", i); |
WiredHome | 1:14319ec53540 | 22 | return i; |
WiredHome | 1:14319ec53540 | 23 | } else { |
WiredHome | 1:14319ec53540 | 24 | fclose(fh); // close this and try the next |
WiredHome | 1:14319ec53540 | 25 | } |
WiredHome | 1:14319ec53540 | 26 | } |
WiredHome | 1:14319ec53540 | 27 | return 0; |
WiredHome | 1:14319ec53540 | 28 | } |
WiredHome | 0:702ce703348d | 29 | |
WiredHome | 0:702ce703348d | 30 | |
WiredHome | 0:702ce703348d | 31 | void drawMandelbrot(float centrex, float centrey, float zoom, int maxIter) { |
WiredHome | 0:702ce703348d | 32 | float xmin = centrex - 1.0/zoom; |
WiredHome | 0:702ce703348d | 33 | float xmax = centrex + 1.0/zoom; |
WiredHome | 0:702ce703348d | 34 | float ymin = centrey - height / (width * zoom); |
WiredHome | 0:702ce703348d | 35 | float ymax = centrey + height / (width *zoom); |
WiredHome | 0:702ce703348d | 36 | float dx = (xmax - xmin) / width; |
WiredHome | 0:702ce703348d | 37 | float dy = (ymax - ymin) / height; |
WiredHome | 0:702ce703348d | 38 | float y = ymin; |
WiredHome | 0:702ce703348d | 39 | float c; |
WiredHome | 0:702ce703348d | 40 | unsigned int cr, cg, cb; |
WiredHome | 0:702ce703348d | 41 | |
WiredHome | 0:702ce703348d | 42 | lcd.SetGraphicsCursor(0, 0); |
WiredHome | 1:14319ec53540 | 43 | // shows use of a pixel (one line scan) buffer. |
WiredHome | 0:702ce703348d | 44 | color_t * pixelBuffer = (color_t *)malloc(width * sizeof(color_t)); |
WiredHome | 0:702ce703348d | 45 | |
WiredHome | 0:702ce703348d | 46 | for (int j = 0; j < height; j++) { |
WiredHome | 0:702ce703348d | 47 | float x = xmin; |
WiredHome | 0:702ce703348d | 48 | |
WiredHome | 0:702ce703348d | 49 | for (int i = 0; i < width; i++) { |
WiredHome | 0:702ce703348d | 50 | float a = x; |
WiredHome | 0:702ce703348d | 51 | float b = y; |
WiredHome | 0:702ce703348d | 52 | int n = 0; |
WiredHome | 0:702ce703348d | 53 | |
WiredHome | 0:702ce703348d | 54 | while (n < maxIter) { |
WiredHome | 0:702ce703348d | 55 | float aa = a * a; |
WiredHome | 0:702ce703348d | 56 | float bb = b * b; |
WiredHome | 0:702ce703348d | 57 | float twoab = 2.0 * a * b; |
WiredHome | 0:702ce703348d | 58 | |
WiredHome | 0:702ce703348d | 59 | a = aa - bb + x; |
WiredHome | 0:702ce703348d | 60 | b = twoab + y; |
WiredHome | 0:702ce703348d | 61 | if(aa + bb > 16.0) { |
WiredHome | 0:702ce703348d | 62 | break; |
WiredHome | 0:702ce703348d | 63 | } |
WiredHome | 0:702ce703348d | 64 | n++; |
WiredHome | 0:702ce703348d | 65 | } |
WiredHome | 0:702ce703348d | 66 | |
WiredHome | 0:702ce703348d | 67 | if (n == maxIter) { |
WiredHome | 0:702ce703348d | 68 | //It's in the set - Black |
WiredHome | 1:14319ec53540 | 69 | pixelBuffer[i] = Black; // if not using the pixel buffer, then lcd.pixel(i,j,Black); |
WiredHome | 0:702ce703348d | 70 | } else { |
WiredHome | 0:702ce703348d | 71 | //Not in the set - pick a colour |
WiredHome | 0:702ce703348d | 72 | c = 3.0 * (maxIter-n)/maxIter; |
WiredHome | 0:702ce703348d | 73 | cr = ((c < 1.0) ? 255 * ( 1.0 - c) : (c > 2.0) ? 255 * (c - 2.0) : 0); |
WiredHome | 0:702ce703348d | 74 | cg = ((c < 1.0) ? 255 * c : (c > 2.0) ? 0 : 255 * (2.0 - c)); |
WiredHome | 0:702ce703348d | 75 | cb = ((c < 1.0) ? 0 : (c > 2.0) ? 255 * (3.0 - c) : 255 * (c - 1.0)); |
WiredHome | 0:702ce703348d | 76 | pixelBuffer[i] = RGB(cr,cg,cb); //lcd.pixel(i,j, RGB(cr,cg,cb)); |
WiredHome | 0:702ce703348d | 77 | } |
WiredHome | 0:702ce703348d | 78 | x += dx; |
WiredHome | 0:702ce703348d | 79 | } |
WiredHome | 0:702ce703348d | 80 | lcd.pixelStream(pixelBuffer, width, 0, j); // send this scanline |
WiredHome | 0:702ce703348d | 81 | y += dy; |
WiredHome | 0:702ce703348d | 82 | } |
WiredHome | 1:14319ec53540 | 83 | free(pixelBuffer); // don't leak memory. |
WiredHome | 0:702ce703348d | 84 | } |
WiredHome | 1:14319ec53540 | 85 | |
WiredHome | 1:14319ec53540 | 86 | |
WiredHome | 1:14319ec53540 | 87 | |
WiredHome | 0:702ce703348d | 88 | int main() |
WiredHome | 0:702ce703348d | 89 | { |
WiredHome | 0:702ce703348d | 90 | Timer timer; |
WiredHome | 1:14319ec53540 | 91 | point_t p; |
WiredHome | 1:14319ec53540 | 92 | |
WiredHome | 0:702ce703348d | 93 | pc.baud(460800); // I like a snappy terminal, so crank it up! |
WiredHome | 0:702ce703348d | 94 | pc.printf("\r\nRA8875 Portrait Mode Dev. - Build " __DATE__ " " __TIME__ "\r\n"); |
WiredHome | 1:14319ec53540 | 95 | pc.printf("Press 'P' to PrintScreen as bmp on local file system\r\n"); |
WiredHome | 1:14319ec53540 | 96 | |
WiredHome | 0:702ce703348d | 97 | lcd.frequency(10000000); |
WiredHome | 0:702ce703348d | 98 | lcd.init(); |
WiredHome | 1:14319ec53540 | 99 | width = lcd.width(); // Could have set the dimensions, let's just adapt. |
WiredHome | 0:702ce703348d | 100 | height = lcd.height(); |
WiredHome | 0:702ce703348d | 101 | |
WiredHome | 0:702ce703348d | 102 | lcd.claim(stdout); // send stdout to the TFT display |
WiredHome | 0:702ce703348d | 103 | lcd.background(Black); // set background to black |
WiredHome | 0:702ce703348d | 104 | lcd.foreground(White); // set chars to white |
WiredHome | 0:702ce703348d | 105 | lcd.cls(); // clear the screen |
WiredHome | 1:14319ec53540 | 106 | lcd.TouchPanelCalibrate("Touch to Calibrate,\r\nthen touch to zoom in,\r\nand touch-hold to zoom out."); |
WiredHome | 0:702ce703348d | 107 | |
WiredHome | 1:14319ec53540 | 108 | //lcd.locate(0,0); |
WiredHome | 0:702ce703348d | 109 | |
WiredHome | 0:702ce703348d | 110 | //Setup base Mandelbrot |
WiredHome | 0:702ce703348d | 111 | float centrex = -0.5; |
WiredHome | 0:702ce703348d | 112 | float centrey = 0.0; |
WiredHome | 0:702ce703348d | 113 | float zoom=0.5; |
WiredHome | 0:702ce703348d | 114 | int maxiterations = 150; |
WiredHome | 0:702ce703348d | 115 | |
WiredHome | 0:702ce703348d | 116 | while(true) { |
WiredHome | 0:702ce703348d | 117 | //Draw it |
WiredHome | 0:702ce703348d | 118 | drawMandelbrot(centrex, centrey, zoom, maxiterations); |
WiredHome | 0:702ce703348d | 119 | |
WiredHome | 0:702ce703348d | 120 | pc.printf("ready for touch\r\n"); |
WiredHome | 1:14319ec53540 | 121 | bool waitingOnUser = true; |
WiredHome | 1:14319ec53540 | 122 | while (waitingOnUser) { |
WiredHome | 1:14319ec53540 | 123 | if (pc.readable()) { |
WiredHome | 1:14319ec53540 | 124 | int c = pc.getc(); |
WiredHome | 1:14319ec53540 | 125 | if (c == 'P') |
WiredHome | 1:14319ec53540 | 126 | GetScreenCapture(); |
WiredHome | 1:14319ec53540 | 127 | } |
WiredHome | 1:14319ec53540 | 128 | if (lcd.TouchPanelReadable()) { |
WiredHome | 1:14319ec53540 | 129 | bool zoomOut = false; |
WiredHome | 1:14319ec53540 | 130 | |
WiredHome | 1:14319ec53540 | 131 | timer.start(); |
WiredHome | 1:14319ec53540 | 132 | timer.reset(); |
WiredHome | 1:14319ec53540 | 133 | while (lcd.TouchPanelReadable(&p)) { |
WiredHome | 1:14319ec53540 | 134 | if (timer.read_ms() > 2000) { |
WiredHome | 1:14319ec53540 | 135 | zoomOut = true; |
WiredHome | 1:14319ec53540 | 136 | break; |
WiredHome | 1:14319ec53540 | 137 | } |
WiredHome | 1:14319ec53540 | 138 | } |
WiredHome | 1:14319ec53540 | 139 | if (zoomOut) { // long held is zoom out. |
WiredHome | 1:14319ec53540 | 140 | // zoom out |
WiredHome | 1:14319ec53540 | 141 | lcd.puts(50, 250, "Zooming out..."); |
WiredHome | 1:14319ec53540 | 142 | pc.printf("zoom out\r\n"); |
WiredHome | 1:14319ec53540 | 143 | centrex = -0.5; |
WiredHome | 1:14319ec53540 | 144 | centrey = 0.0; |
WiredHome | 1:14319ec53540 | 145 | zoom=0.5; |
WiredHome | 1:14319ec53540 | 146 | } else { |
WiredHome | 1:14319ec53540 | 147 | //Set new centre and zoom |
WiredHome | 1:14319ec53540 | 148 | lcd.puts(50, 250, "Zooming in..."); |
WiredHome | 1:14319ec53540 | 149 | pc.printf("zoom in\r\n"); |
WiredHome | 1:14319ec53540 | 150 | centrex += (2.0 * p.x - width) / (zoom * height); |
WiredHome | 1:14319ec53540 | 151 | centrey += (2.0 * p.y - height) / (zoom * width); |
WiredHome | 1:14319ec53540 | 152 | zoom *= 4.0; |
WiredHome | 1:14319ec53540 | 153 | lcd.rect(p.x - width / 8.0, p.y - height / 8.0, |
WiredHome | 1:14319ec53540 | 154 | p.x + width / 8.0, p.y + height / 8.0, Yellow); |
WiredHome | 1:14319ec53540 | 155 | } |
WiredHome | 1:14319ec53540 | 156 | waitingOnUser = false; |
WiredHome | 1:14319ec53540 | 157 | } |
WiredHome | 0:702ce703348d | 158 | } |
WiredHome | 0:702ce703348d | 159 | } |
WiredHome | 0:702ce703348d | 160 | } |
WiredHome | 0:702ce703348d | 161 |