5 by 14 Neo array
Dependencies: mbed
NeoMatrix/NeoMatrix.cpp@0:a32d1a85a830, 2017-06-12 (annotated)
- Committer:
- RogerJKelly
- Date:
- Mon Jun 12 16:57:43 2017 +0000
- Revision:
- 0:a32d1a85a830
working display using ARM to drive display.
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
RogerJKelly | 0:a32d1a85a830 | 1 | /********************************************** |
RogerJKelly | 0:a32d1a85a830 | 2 | * NeoMatrix.cpp |
RogerJKelly | 0:a32d1a85a830 | 3 | * |
RogerJKelly | 0:a32d1a85a830 | 4 | * Taylor Powell |
RogerJKelly | 0:a32d1a85a830 | 5 | * March 2015 |
RogerJKelly | 0:a32d1a85a830 | 6 | * |
RogerJKelly | 0:a32d1a85a830 | 7 | * Controls an Adafruit Neopixel NeoMatrix 8x8 |
RogerJKelly | 0:a32d1a85a830 | 8 | * Because of the global nature of the IO register and bitmask variables, only one contiguous chain of NeoMatrix Arrays can be connected |
RogerJKelly | 0:a32d1a85a830 | 9 | * A large number of NeoMatrix arrays can be chained together by tying Din to Dout of sucessive arrays, but an external power sourece may be required |
RogerJKelly | 0:a32d1a85a830 | 10 | * |
RogerJKelly | 0:a32d1a85a830 | 11 | * This library supports only the NXP LPC1768 |
RogerJKelly | 0:a32d1a85a830 | 12 | */ |
RogerJKelly | 0:a32d1a85a830 | 13 | |
RogerJKelly | 0:a32d1a85a830 | 14 | #include "mbed.h" |
RogerJKelly | 0:a32d1a85a830 | 15 | #include "NeoMatrix.h" |
RogerJKelly | 0:a32d1a85a830 | 16 | #include "font.h" |
RogerJKelly | 0:a32d1a85a830 | 17 | |
RogerJKelly | 0:a32d1a85a830 | 18 | |
RogerJKelly | 0:a32d1a85a830 | 19 | // FastIO register address and bitmask for the GPIO pin |
RogerJKelly | 0:a32d1a85a830 | 20 | // because these are imported in the assembly |
RogerJKelly | 0:a32d1a85a830 | 21 | //uint32_t neo_fio_reg; |
RogerJKelly | 0:a32d1a85a830 | 22 | //uint32_t neo_bitmask; |
RogerJKelly | 0:a32d1a85a830 | 23 | |
RogerJKelly | 0:a32d1a85a830 | 24 | // function to write to the strip, implemented in ARM assembly |
RogerJKelly | 0:a32d1a85a830 | 25 | //extern "C" void neo_out(NeoColor*, int); |
RogerJKelly | 0:a32d1a85a830 | 26 | |
RogerJKelly | 0:a32d1a85a830 | 27 | #define max(a,b) \ |
RogerJKelly | 0:a32d1a85a830 | 28 | ({ __typeof__ (a) _a = (a); \ |
RogerJKelly | 0:a32d1a85a830 | 29 | __typeof__ (b) _b = (b); \ |
RogerJKelly | 0:a32d1a85a830 | 30 | _a > _b ? _a : _b; }) |
RogerJKelly | 0:a32d1a85a830 | 31 | |
RogerJKelly | 0:a32d1a85a830 | 32 | #define min(a,b) \ |
RogerJKelly | 0:a32d1a85a830 | 33 | ({ __typeof__ (a) _a = (a); \ |
RogerJKelly | 0:a32d1a85a830 | 34 | __typeof__ (b) _b = (b); \ |
RogerJKelly | 0:a32d1a85a830 | 35 | _a < _b ? _a : _b; }) |
RogerJKelly | 0:a32d1a85a830 | 36 | |
RogerJKelly | 0:a32d1a85a830 | 37 | |
RogerJKelly | 0:a32d1a85a830 | 38 | //__gpo(pin) |
RogerJKelly | 0:a32d1a85a830 | 39 | NeoArr::NeoArr(PinName pin, int N, int zeroHigh, int zeroLow, int oneHigh, int oneLow) : N(N), __gpo(pin) |
RogerJKelly | 0:a32d1a85a830 | 40 | { |
RogerJKelly | 0:a32d1a85a830 | 41 | bright = 0.2; |
RogerJKelly | 0:a32d1a85a830 | 42 | Nbytes = N * 70 * 3; // changed from 64 to 70 - 14 x 5 |
RogerJKelly | 0:a32d1a85a830 | 43 | arr = (NeoColor*)malloc(N * 70 * sizeof(NeoColor)); |
RogerJKelly | 0:a32d1a85a830 | 44 | if (arr == NULL) |
RogerJKelly | 0:a32d1a85a830 | 45 | { |
RogerJKelly | 0:a32d1a85a830 | 46 | printf("NeoArr: ERROR unable to malloc pixel array data"); |
RogerJKelly | 0:a32d1a85a830 | 47 | N = 0; |
RogerJKelly | 0:a32d1a85a830 | 48 | } |
RogerJKelly | 0:a32d1a85a830 | 49 | |
RogerJKelly | 0:a32d1a85a830 | 50 | __size = N * 70; // changed from 64 to 70 - 14 x 5 |
RogerJKelly | 0:a32d1a85a830 | 51 | __transmitBuf = new bool[__size * FRAME_SIZE]; |
RogerJKelly | 0:a32d1a85a830 | 52 | |
RogerJKelly | 0:a32d1a85a830 | 53 | //gpio_init(&gpio, pin, PIN_OUTPUT); // initialize GPIO registers |
RogerJKelly | 0:a32d1a85a830 | 54 | //neo_fio_reg = (uint32_t)gpio.reg_dir; // set registers and bitmask for |
RogerJKelly | 0:a32d1a85a830 | 55 | //neo_bitmask = 1 << ((int)pin & 0x1F); // the assembly to use |
RogerJKelly | 0:a32d1a85a830 | 56 | |
RogerJKelly | 0:a32d1a85a830 | 57 | // IO pin to use |
RogerJKelly | 0:a32d1a85a830 | 58 | __outPin = pin; |
RogerJKelly | 0:a32d1a85a830 | 59 | // Default values designed for K64f. Assumes GPIO toggle takes ~0.4us |
RogerJKelly | 0:a32d1a85a830 | 60 | setDelays(zeroHigh, zeroLow, oneHigh, oneLow); |
RogerJKelly | 0:a32d1a85a830 | 61 | } |
RogerJKelly | 0:a32d1a85a830 | 62 | |
RogerJKelly | 0:a32d1a85a830 | 63 | void NeoArr::setDelays(int zeroHigh, int zeroLow, int oneHigh, int oneLow) |
RogerJKelly | 0:a32d1a85a830 | 64 | { |
RogerJKelly | 0:a32d1a85a830 | 65 | __zeroHigh = zeroHigh; |
RogerJKelly | 0:a32d1a85a830 | 66 | __zeroLow = zeroLow; |
RogerJKelly | 0:a32d1a85a830 | 67 | __oneHigh = oneHigh; |
RogerJKelly | 0:a32d1a85a830 | 68 | __oneLow = oneLow; |
RogerJKelly | 0:a32d1a85a830 | 69 | } |
RogerJKelly | 0:a32d1a85a830 | 70 | |
RogerJKelly | 0:a32d1a85a830 | 71 | void NeoArr::setBrightness(float bright) |
RogerJKelly | 0:a32d1a85a830 | 72 | { |
RogerJKelly | 0:a32d1a85a830 | 73 | this->bright = bright; |
RogerJKelly | 0:a32d1a85a830 | 74 | } |
RogerJKelly | 0:a32d1a85a830 | 75 | |
RogerJKelly | 0:a32d1a85a830 | 76 | |
RogerJKelly | 0:a32d1a85a830 | 77 | void NeoArr::setPixel(int idx, int x, int y, int color) |
RogerJKelly | 0:a32d1a85a830 | 78 | { |
RogerJKelly | 0:a32d1a85a830 | 79 | int red = (color & 0xFF0000) >> 16; |
RogerJKelly | 0:a32d1a85a830 | 80 | int green = (color & 0x00FF00) >> 8; |
RogerJKelly | 0:a32d1a85a830 | 81 | int blue = (color & 0x0000FF); |
RogerJKelly | 0:a32d1a85a830 | 82 | |
RogerJKelly | 0:a32d1a85a830 | 83 | setPixel(idx, x, y, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 84 | } |
RogerJKelly | 0:a32d1a85a830 | 85 | |
RogerJKelly | 0:a32d1a85a830 | 86 | void NeoArr::setPixel(int idx, int x, int y, uint8_t red, uint8_t green, uint8_t blue) |
RogerJKelly | 0:a32d1a85a830 | 87 | { |
RogerJKelly | 0:a32d1a85a830 | 88 | //int pixel = idx*64 + x*8 + y; // specify pixel based on board index, x, and y values |
RogerJKelly | 0:a32d1a85a830 | 89 | //int pixel = idx*70 + x*14 + y; // specify pixel based on board index, x, and y values |
RogerJKelly | 0:a32d1a85a830 | 90 | int pixel = x + y*14; // specify pixel based x and y values |
RogerJKelly | 0:a32d1a85a830 | 91 | // modulate pixel by the total number of pixels |
RogerJKelly | 0:a32d1a85a830 | 92 | arr[pixel % (N*70)].red = (uint8_t)(red * bright); |
RogerJKelly | 0:a32d1a85a830 | 93 | arr[pixel % (N*70)].green = (uint8_t)(green * bright); |
RogerJKelly | 0:a32d1a85a830 | 94 | arr[pixel % (N*70)].blue = (uint8_t)(blue * bright); |
RogerJKelly | 0:a32d1a85a830 | 95 | } |
RogerJKelly | 0:a32d1a85a830 | 96 | |
RogerJKelly | 0:a32d1a85a830 | 97 | void NeoArr::drawLine(int idx, int x1, int y1, int x2, int y2, int color) |
RogerJKelly | 0:a32d1a85a830 | 98 | { |
RogerJKelly | 0:a32d1a85a830 | 99 | int red = (color & 0xFF0000) >> 16; |
RogerJKelly | 0:a32d1a85a830 | 100 | int green = (color & 0x00FF00) >> 8; |
RogerJKelly | 0:a32d1a85a830 | 101 | int blue = (color & 0x0000FF); |
RogerJKelly | 0:a32d1a85a830 | 102 | |
RogerJKelly | 0:a32d1a85a830 | 103 | drawLine(idx, x1, y1, x2,y2, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 104 | } |
RogerJKelly | 0:a32d1a85a830 | 105 | |
RogerJKelly | 0:a32d1a85a830 | 106 | void NeoArr::drawLine(int idx, int x1, int y1, int x2, int y2, uint8_t red, uint8_t green, uint8_t blue) |
RogerJKelly | 0:a32d1a85a830 | 107 | { |
RogerJKelly | 0:a32d1a85a830 | 108 | float k; |
RogerJKelly | 0:a32d1a85a830 | 109 | int j = rint(sqrt(pow((x1-x2),2.0) + pow((y1-y2),2.0))); // calculates magnitude of line |
RogerJKelly | 0:a32d1a85a830 | 110 | if(x1 != x2) // handle infinite case |
RogerJKelly | 0:a32d1a85a830 | 111 | k = atan2( (float)(y2-y1),(float) ( x2-x1)); // calculates angle of line |
RogerJKelly | 0:a32d1a85a830 | 112 | else |
RogerJKelly | 0:a32d1a85a830 | 113 | k = acos(0.0); |
RogerJKelly | 0:a32d1a85a830 | 114 | |
RogerJKelly | 0:a32d1a85a830 | 115 | for(float n=0; n<=j; n++) // set a number pixels equal to the magnitude of the line along the closest (rounded) line |
RogerJKelly | 0:a32d1a85a830 | 116 | if((x1+ rint(n*cos(k))) >=0 && (x1+rint( n*cos(k))) <=7 && (y1+rint(n*sin(k)))>=0 && (y1+rint(n*sin(k)))<=7) |
RogerJKelly | 0:a32d1a85a830 | 117 | setPixel(idx, x1+ rint(n*cos(k)), y1+ rint(n*sin(k)), red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 118 | |
RogerJKelly | 0:a32d1a85a830 | 119 | |
RogerJKelly | 0:a32d1a85a830 | 120 | } |
RogerJKelly | 0:a32d1a85a830 | 121 | |
RogerJKelly | 0:a32d1a85a830 | 122 | void NeoArr::drawRect(int idx, int x1, int y1, int x2, int y2, int color) |
RogerJKelly | 0:a32d1a85a830 | 123 | { |
RogerJKelly | 0:a32d1a85a830 | 124 | int red = (color & 0xFF0000) >> 16; |
RogerJKelly | 0:a32d1a85a830 | 125 | int green = (color & 0x00FF00) >> 8; |
RogerJKelly | 0:a32d1a85a830 | 126 | int blue = (color & 0x0000FF); |
RogerJKelly | 0:a32d1a85a830 | 127 | |
RogerJKelly | 0:a32d1a85a830 | 128 | drawRect(idx, x1, y1, x2,y2, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 129 | } |
RogerJKelly | 0:a32d1a85a830 | 130 | |
RogerJKelly | 0:a32d1a85a830 | 131 | void NeoArr::drawRect(int idx, int x1, int y1, int x2, int y2, uint8_t red, uint8_t green, uint8_t blue) |
RogerJKelly | 0:a32d1a85a830 | 132 | { |
RogerJKelly | 0:a32d1a85a830 | 133 | // note: drawRect does not use drawLine function because the angles will always be 90 degrees and so for these for loops are faster |
RogerJKelly | 0:a32d1a85a830 | 134 | for(int i=0; i<=(abs(x2-x1)); i++){ // draws horizontal lines |
RogerJKelly | 0:a32d1a85a830 | 135 | if ((max(x1,x2)-i) >= 0 && max(x1, x2) -i <=7){ |
RogerJKelly | 0:a32d1a85a830 | 136 | if(max(y1,y2) <= 7) |
RogerJKelly | 0:a32d1a85a830 | 137 | setPixel(idx, max(x1,x2)-i, max(y1,y2), red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 138 | |
RogerJKelly | 0:a32d1a85a830 | 139 | if(min(y1,y2) >= 0) |
RogerJKelly | 0:a32d1a85a830 | 140 | setPixel(idx, max(x1,x2)-i, min(y1,y2), red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 141 | } |
RogerJKelly | 0:a32d1a85a830 | 142 | } |
RogerJKelly | 0:a32d1a85a830 | 143 | |
RogerJKelly | 0:a32d1a85a830 | 144 | for(int i=0; i<=(abs(y2-y1)); i++){ // draws verticle lines |
RogerJKelly | 0:a32d1a85a830 | 145 | if ((max(y1,y2)-i) >= 0 && max(y1, y2) -i <=7){ |
RogerJKelly | 0:a32d1a85a830 | 146 | if(max(x1,x2) <= 7) |
RogerJKelly | 0:a32d1a85a830 | 147 | setPixel(idx, max(x1,x2), max(y1,y2)-i, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 148 | |
RogerJKelly | 0:a32d1a85a830 | 149 | if(min(x1,x2) >= 0) |
RogerJKelly | 0:a32d1a85a830 | 150 | setPixel(idx, min(x1,x2), max(y1,y2)-i, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 151 | } |
RogerJKelly | 0:a32d1a85a830 | 152 | } |
RogerJKelly | 0:a32d1a85a830 | 153 | } |
RogerJKelly | 0:a32d1a85a830 | 154 | |
RogerJKelly | 0:a32d1a85a830 | 155 | |
RogerJKelly | 0:a32d1a85a830 | 156 | void NeoArr::drawFilledRect(int idx, int x1, int y1, int x2, int y2, int color) |
RogerJKelly | 0:a32d1a85a830 | 157 | { |
RogerJKelly | 0:a32d1a85a830 | 158 | int red = (color & 0xFF0000) >> 16; |
RogerJKelly | 0:a32d1a85a830 | 159 | int green = (color & 0x00FF00) >> 8; |
RogerJKelly | 0:a32d1a85a830 | 160 | int blue = (color & 0x0000FF); |
RogerJKelly | 0:a32d1a85a830 | 161 | |
RogerJKelly | 0:a32d1a85a830 | 162 | drawFilledRect(idx, x1, y1, x2,y2, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 163 | } |
RogerJKelly | 0:a32d1a85a830 | 164 | |
RogerJKelly | 0:a32d1a85a830 | 165 | void NeoArr::drawFilledRect(int idx, int x1, int y1, int x2, int y2, uint8_t red, uint8_t green, uint8_t blue) |
RogerJKelly | 0:a32d1a85a830 | 166 | { |
RogerJKelly | 0:a32d1a85a830 | 167 | for(int i=0; i<=(abs(x2-x1)); i++){ |
RogerJKelly | 0:a32d1a85a830 | 168 | if ((max(x1,x2)-i) >= 0 && max(x1, x2) -i <=7){ |
RogerJKelly | 0:a32d1a85a830 | 169 | for(int n=0; n<=(abs(y2-y1)); n++){ |
RogerJKelly | 0:a32d1a85a830 | 170 | if((max(y1,y2)-n) >= 0 && max(y1, y2)-n <=7){ |
RogerJKelly | 0:a32d1a85a830 | 171 | setPixel(idx, max(x1,x2)-i, max(y1,y2)-n, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 172 | } |
RogerJKelly | 0:a32d1a85a830 | 173 | } |
RogerJKelly | 0:a32d1a85a830 | 174 | } |
RogerJKelly | 0:a32d1a85a830 | 175 | } |
RogerJKelly | 0:a32d1a85a830 | 176 | |
RogerJKelly | 0:a32d1a85a830 | 177 | } |
RogerJKelly | 0:a32d1a85a830 | 178 | |
RogerJKelly | 0:a32d1a85a830 | 179 | void NeoArr::fillScreen(int idx, int color) |
RogerJKelly | 0:a32d1a85a830 | 180 | { |
RogerJKelly | 0:a32d1a85a830 | 181 | int red = (color & 0xFF0000) >> 16; |
RogerJKelly | 0:a32d1a85a830 | 182 | int green = (color & 0x00FF00) >> 8; |
RogerJKelly | 0:a32d1a85a830 | 183 | int blue = (color & 0x0000FF); |
RogerJKelly | 0:a32d1a85a830 | 184 | |
RogerJKelly | 0:a32d1a85a830 | 185 | fillScreen(idx, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 186 | } |
RogerJKelly | 0:a32d1a85a830 | 187 | |
RogerJKelly | 0:a32d1a85a830 | 188 | // adjusted for 14 x 5 screen |
RogerJKelly | 0:a32d1a85a830 | 189 | void NeoArr::fillScreen(int idx,uint8_t red, uint8_t green, uint8_t blue) |
RogerJKelly | 0:a32d1a85a830 | 190 | { |
RogerJKelly | 0:a32d1a85a830 | 191 | for(int i=0; i<14; i++) |
RogerJKelly | 0:a32d1a85a830 | 192 | for(int n=0; n<5; n++) |
RogerJKelly | 0:a32d1a85a830 | 193 | setPixel(idx, i, n, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 194 | } |
RogerJKelly | 0:a32d1a85a830 | 195 | |
RogerJKelly | 0:a32d1a85a830 | 196 | |
RogerJKelly | 0:a32d1a85a830 | 197 | void NeoArr::drawTriangle(int idx, int x1, int y1, int x2, int y2, int x3, int y3, int color) |
RogerJKelly | 0:a32d1a85a830 | 198 | { |
RogerJKelly | 0:a32d1a85a830 | 199 | int red = (color & 0xFF0000) >> 16; |
RogerJKelly | 0:a32d1a85a830 | 200 | int green = (color & 0x00FF00) >> 8; |
RogerJKelly | 0:a32d1a85a830 | 201 | int blue = (color & 0x0000FF); |
RogerJKelly | 0:a32d1a85a830 | 202 | |
RogerJKelly | 0:a32d1a85a830 | 203 | drawTriangle(idx, x1, y1, x2,y2, x3, y3, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 204 | } |
RogerJKelly | 0:a32d1a85a830 | 205 | |
RogerJKelly | 0:a32d1a85a830 | 206 | void NeoArr::drawTriangle(int idx, int x1, int y1, int x2, int y2, int x3, int y3, uint8_t red, uint8_t green, uint8_t blue) |
RogerJKelly | 0:a32d1a85a830 | 207 | { |
RogerJKelly | 0:a32d1a85a830 | 208 | |
RogerJKelly | 0:a32d1a85a830 | 209 | drawLine(idx, x1, y1, x2, y2, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 210 | drawLine(idx, x2, y2, x3, y3, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 211 | drawLine(idx, x3, y3, x1, y1, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 212 | |
RogerJKelly | 0:a32d1a85a830 | 213 | } |
RogerJKelly | 0:a32d1a85a830 | 214 | |
RogerJKelly | 0:a32d1a85a830 | 215 | void NeoArr::drawFilledTriangle(int idx, int x1, int y1, int x2, int y2, int x3, int y3, int color) |
RogerJKelly | 0:a32d1a85a830 | 216 | { |
RogerJKelly | 0:a32d1a85a830 | 217 | int red = (color & 0xFF0000) >> 16; |
RogerJKelly | 0:a32d1a85a830 | 218 | int green = (color & 0x00FF00) >> 8; |
RogerJKelly | 0:a32d1a85a830 | 219 | int blue = (color & 0x0000FF); |
RogerJKelly | 0:a32d1a85a830 | 220 | |
RogerJKelly | 0:a32d1a85a830 | 221 | drawFilledTriangle(idx, x1, y1, x2,y2, x3, y3, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 222 | } |
RogerJKelly | 0:a32d1a85a830 | 223 | |
RogerJKelly | 0:a32d1a85a830 | 224 | void NeoArr::drawFilledTriangle(int idx, int x1, int y1, int x2, int y2, int x3, int y3, uint8_t red, uint8_t green, uint8_t blue) |
RogerJKelly | 0:a32d1a85a830 | 225 | { |
RogerJKelly | 0:a32d1a85a830 | 226 | // note: drawFilledTriangle draws two legs of the triangle and then draws lines from their corner to each point on the opposite leg |
RogerJKelly | 0:a32d1a85a830 | 227 | drawLine(idx, x1, y1, x2, y2, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 228 | drawLine(idx, x2, y2, x3, y3, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 229 | |
RogerJKelly | 0:a32d1a85a830 | 230 | |
RogerJKelly | 0:a32d1a85a830 | 231 | float k; |
RogerJKelly | 0:a32d1a85a830 | 232 | int j = rint(sqrt(pow((x1-x3),2.0) + pow((y1-y3),2.0))); // magnitude of opposite leg |
RogerJKelly | 0:a32d1a85a830 | 233 | if(x1 != x3) |
RogerJKelly | 0:a32d1a85a830 | 234 | k = atan2( (float)(y3-y1),(float) ( x3-x1)); // angle of line of opposite leg |
RogerJKelly | 0:a32d1a85a830 | 235 | else |
RogerJKelly | 0:a32d1a85a830 | 236 | k = acos(0.0); |
RogerJKelly | 0:a32d1a85a830 | 237 | |
RogerJKelly | 0:a32d1a85a830 | 238 | for(float n=0; n<=j; n++) |
RogerJKelly | 0:a32d1a85a830 | 239 | if((x1+ rint(n*cos(k))) >=0 && (x1+rint( n*cos(k))) <=7 && (y1+rint(n*sin(k)))>=0 && (y1+rint(n*sin(k)))<=7) |
RogerJKelly | 0:a32d1a85a830 | 240 | drawLine(idx, x1+ rint(n*cos(k)), y1+ rint(n*sin(k)), x2, y2, red, green, blue); // draw line from corner to each point on opposite leg |
RogerJKelly | 0:a32d1a85a830 | 241 | } |
RogerJKelly | 0:a32d1a85a830 | 242 | |
RogerJKelly | 0:a32d1a85a830 | 243 | void NeoArr::drawChar(int idx, int x, int y, char c, int color) |
RogerJKelly | 0:a32d1a85a830 | 244 | { |
RogerJKelly | 0:a32d1a85a830 | 245 | int red = (color & 0xFF0000) >> 16; |
RogerJKelly | 0:a32d1a85a830 | 246 | int green = (color & 0x00FF00) >> 8; |
RogerJKelly | 0:a32d1a85a830 | 247 | int blue = (color & 0x0000FF); |
RogerJKelly | 0:a32d1a85a830 | 248 | |
RogerJKelly | 0:a32d1a85a830 | 249 | drawChar(idx, x, y, c, red, green, blue); |
RogerJKelly | 0:a32d1a85a830 | 250 | } |
RogerJKelly | 0:a32d1a85a830 | 251 | |
RogerJKelly | 0:a32d1a85a830 | 252 | void NeoArr::drawChar(int idx, int x, int y, char c, uint8_t red, uint8_t green, uint8_t blue) |
RogerJKelly | 0:a32d1a85a830 | 253 | { |
RogerJKelly | 0:a32d1a85a830 | 254 | uint8_t i,j; |
RogerJKelly | 0:a32d1a85a830 | 255 | |
RogerJKelly | 0:a32d1a85a830 | 256 | c = c & 0x7F; // mask c to avoid errors |
RogerJKelly | 0:a32d1a85a830 | 257 | |
RogerJKelly | 0:a32d1a85a830 | 258 | if (c < ' ') { // convert c into index of font array |
RogerJKelly | 0:a32d1a85a830 | 259 | c = 0; |
RogerJKelly | 0:a32d1a85a830 | 260 | } else { |
RogerJKelly | 0:a32d1a85a830 | 261 | c -= ' '; |
RogerJKelly | 0:a32d1a85a830 | 262 | } |
RogerJKelly | 0:a32d1a85a830 | 263 | |
RogerJKelly | 0:a32d1a85a830 | 264 | // font is BMplain, a 96x6 array stored in font.h, many free available fonts are online and can be swapped into this font |
RogerJKelly | 0:a32d1a85a830 | 265 | const uint8_t* chr = font[c]; |
RogerJKelly | 0:a32d1a85a830 | 266 | |
RogerJKelly | 0:a32d1a85a830 | 267 | for (j=0; j<6; j++) // character width is 6 |
RogerJKelly | 0:a32d1a85a830 | 268 | { |
RogerJKelly | 0:a32d1a85a830 | 269 | for (i=0; i<5; i++) // character height is 5 - changed from 8 |
RogerJKelly | 0:a32d1a85a830 | 270 | { |
RogerJKelly | 0:a32d1a85a830 | 271 | if (chr[j] & (1<<(i))) // if there is a pixel in the vertical line, set pixel on board |
RogerJKelly | 0:a32d1a85a830 | 272 | { |
RogerJKelly | 0:a32d1a85a830 | 273 | //if((x+j) <= 13 && (x+j)>=0 && (y+4-i)>=0 && (y+4-i) <=4) |
RogerJKelly | 0:a32d1a85a830 | 274 | setPixel(0, x+j, y+i, red,green,blue); |
RogerJKelly | 0:a32d1a85a830 | 275 | } |
RogerJKelly | 0:a32d1a85a830 | 276 | } |
RogerJKelly | 0:a32d1a85a830 | 277 | } |
RogerJKelly | 0:a32d1a85a830 | 278 | } |
RogerJKelly | 0:a32d1a85a830 | 279 | |
RogerJKelly | 0:a32d1a85a830 | 280 | void NeoArr::showImage(int idx, const int *img) |
RogerJKelly | 0:a32d1a85a830 | 281 | { |
RogerJKelly | 0:a32d1a85a830 | 282 | int r, g, b; |
RogerJKelly | 0:a32d1a85a830 | 283 | for (int i = 0; i < 8; i++) |
RogerJKelly | 0:a32d1a85a830 | 284 | { |
RogerJKelly | 0:a32d1a85a830 | 285 | for(int n=0; n<8;n++) |
RogerJKelly | 0:a32d1a85a830 | 286 | { |
RogerJKelly | 0:a32d1a85a830 | 287 | r = (img[i] & 0xFF0000) >> 16; |
RogerJKelly | 0:a32d1a85a830 | 288 | g = (img[i] & 0x00FF00) >>8; |
RogerJKelly | 0:a32d1a85a830 | 289 | b = img[i] & 0x0000FF; |
RogerJKelly | 0:a32d1a85a830 | 290 | setPixel(idx,i,n, r, g, b); |
RogerJKelly | 0:a32d1a85a830 | 291 | } |
RogerJKelly | 0:a32d1a85a830 | 292 | } |
RogerJKelly | 0:a32d1a85a830 | 293 | } |
RogerJKelly | 0:a32d1a85a830 | 294 | |
RogerJKelly | 0:a32d1a85a830 | 295 | void NeoArr::showImageRGB(int idx, int bmp, int r, int g, int b) |
RogerJKelly | 0:a32d1a85a830 | 296 | { |
RogerJKelly | 0:a32d1a85a830 | 297 | //int r, g, b; |
RogerJKelly | 0:a32d1a85a830 | 298 | bmp &= 0x03; // bounds check on the index |
RogerJKelly | 0:a32d1a85a830 | 299 | const unsigned char* img = smile_img[bmp]; |
RogerJKelly | 0:a32d1a85a830 | 300 | for (int i = 0; i < 8; i++) // each byte in image file |
RogerJKelly | 0:a32d1a85a830 | 301 | { |
RogerJKelly | 0:a32d1a85a830 | 302 | for(int n=0; n<8;n++) // for each bit |
RogerJKelly | 0:a32d1a85a830 | 303 | { |
RogerJKelly | 0:a32d1a85a830 | 304 | if ( ((img[i] << n) & 0x80) == 0x80 ) |
RogerJKelly | 0:a32d1a85a830 | 305 | setPixel(idx,i,n, r, g, b); |
RogerJKelly | 0:a32d1a85a830 | 306 | } |
RogerJKelly | 0:a32d1a85a830 | 307 | } |
RogerJKelly | 0:a32d1a85a830 | 308 | } |
RogerJKelly | 0:a32d1a85a830 | 309 | |
RogerJKelly | 0:a32d1a85a830 | 310 | void NeoArr::clear() |
RogerJKelly | 0:a32d1a85a830 | 311 | { |
RogerJKelly | 0:a32d1a85a830 | 312 | for (int i = 0; i < (N*70); i++) // changed from 64 to 70 - 14 x 5 |
RogerJKelly | 0:a32d1a85a830 | 313 | { |
RogerJKelly | 0:a32d1a85a830 | 314 | arr[i].red = 0; |
RogerJKelly | 0:a32d1a85a830 | 315 | arr[i].green = 0; |
RogerJKelly | 0:a32d1a85a830 | 316 | arr[i].blue = 0; |
RogerJKelly | 0:a32d1a85a830 | 317 | } |
RogerJKelly | 0:a32d1a85a830 | 318 | } |
RogerJKelly | 0:a32d1a85a830 | 319 | |
RogerJKelly | 0:a32d1a85a830 | 320 | /*************************************************************** |
RogerJKelly | 0:a32d1a85a830 | 321 | // original NeoArr::write -- |
RogerJKelly | 0:a32d1a85a830 | 322 | void NeoArr::write() |
RogerJKelly | 0:a32d1a85a830 | 323 | { |
RogerJKelly | 0:a32d1a85a830 | 324 | __disable_irq(); // disable interrupts |
RogerJKelly | 0:a32d1a85a830 | 325 | neo_out(arr, Nbytes); // output to the strip |
RogerJKelly | 0:a32d1a85a830 | 326 | __enable_irq(); // enable interrupts |
RogerJKelly | 0:a32d1a85a830 | 327 | wait_us(50); // wait 50us for the reset pulse |
RogerJKelly | 0:a32d1a85a830 | 328 | } |
RogerJKelly | 0:a32d1a85a830 | 329 | ***************************************************************/ |
RogerJKelly | 0:a32d1a85a830 | 330 | |
RogerJKelly | 0:a32d1a85a830 | 331 | void NeoArr::__loadBuf() |
RogerJKelly | 0:a32d1a85a830 | 332 | { |
RogerJKelly | 0:a32d1a85a830 | 333 | for (int i = 0; i < __size; i++) |
RogerJKelly | 0:a32d1a85a830 | 334 | { |
RogerJKelly | 0:a32d1a85a830 | 335 | unsigned char agrb[3] = {0x0, 0x0, 0x0}; |
RogerJKelly | 0:a32d1a85a830 | 336 | |
RogerJKelly | 0:a32d1a85a830 | 337 | // 0 = green, 1 = red, 2 = blue, 3 = brightness |
RogerJKelly | 0:a32d1a85a830 | 338 | agrb[0] = arr[i % (N*70)].green; // changed from 64 to 70 - 14 x 5 |
RogerJKelly | 0:a32d1a85a830 | 339 | agrb[1] = arr[i % (N*70)].red; // changed from 64 to 70 - 14 x 5 |
RogerJKelly | 0:a32d1a85a830 | 340 | agrb[2] = arr[i % (N*70)].blue; // changed from 64 to 70 - 14 x 5 |
RogerJKelly | 0:a32d1a85a830 | 341 | //agrb[3] = (color & 0xFF000000) >> 24; |
RogerJKelly | 0:a32d1a85a830 | 342 | |
RogerJKelly | 0:a32d1a85a830 | 343 | // load transmit buffer |
RogerJKelly | 0:a32d1a85a830 | 344 | for (int clr = 0; clr < 3; clr++) // for each color |
RogerJKelly | 0:a32d1a85a830 | 345 | { |
RogerJKelly | 0:a32d1a85a830 | 346 | for (int j = 0; j < 8; j++) // for each bit |
RogerJKelly | 0:a32d1a85a830 | 347 | { |
RogerJKelly | 0:a32d1a85a830 | 348 | if (((agrb[clr] << j) & 0x80) == 0x80) |
RogerJKelly | 0:a32d1a85a830 | 349 | { |
RogerJKelly | 0:a32d1a85a830 | 350 | // Bit is set (checks MSB fist) |
RogerJKelly | 0:a32d1a85a830 | 351 | __transmitBuf[(i * FRAME_SIZE) + (clr * 8) + j] = 1; |
RogerJKelly | 0:a32d1a85a830 | 352 | } else { |
RogerJKelly | 0:a32d1a85a830 | 353 | // Bit is clear |
RogerJKelly | 0:a32d1a85a830 | 354 | __transmitBuf[(i * FRAME_SIZE) + (clr * 8) + j] = 0; |
RogerJKelly | 0:a32d1a85a830 | 355 | } |
RogerJKelly | 0:a32d1a85a830 | 356 | } |
RogerJKelly | 0:a32d1a85a830 | 357 | } |
RogerJKelly | 0:a32d1a85a830 | 358 | } |
RogerJKelly | 0:a32d1a85a830 | 359 | } |
RogerJKelly | 0:a32d1a85a830 | 360 | |
RogerJKelly | 0:a32d1a85a830 | 361 | //void NeoArr::write_offsets (int buf[],int r_offset, int g_offset, int b_offset) |
RogerJKelly | 0:a32d1a85a830 | 362 | void NeoArr::write() |
RogerJKelly | 0:a32d1a85a830 | 363 | { |
RogerJKelly | 0:a32d1a85a830 | 364 | int i, j; |
RogerJKelly | 0:a32d1a85a830 | 365 | |
RogerJKelly | 0:a32d1a85a830 | 366 | // Load the transmit buffer. |
RogerJKelly | 0:a32d1a85a830 | 367 | // transmit buffer is array where each byte represents one bit in the pixel buffer |
RogerJKelly | 0:a32d1a85a830 | 368 | // 24 bytes per pixel * 64 pixels = 1536 bytes of ram |
RogerJKelly | 0:a32d1a85a830 | 369 | __loadBuf(); |
RogerJKelly | 0:a32d1a85a830 | 370 | |
RogerJKelly | 0:a32d1a85a830 | 371 | // Entering timing critical section, so disabling interrupts |
RogerJKelly | 0:a32d1a85a830 | 372 | __disable_irq(); |
RogerJKelly | 0:a32d1a85a830 | 373 | |
RogerJKelly | 0:a32d1a85a830 | 374 | // Begin bit-banging |
RogerJKelly | 0:a32d1a85a830 | 375 | for (i = 0; i < FRAME_SIZE * __size; i++) { |
RogerJKelly | 0:a32d1a85a830 | 376 | j = 0; |
RogerJKelly | 0:a32d1a85a830 | 377 | if (__transmitBuf[i]){ |
RogerJKelly | 0:a32d1a85a830 | 378 | __gpo = 1; |
RogerJKelly | 0:a32d1a85a830 | 379 | for (; j < __oneHigh; j++) { |
RogerJKelly | 0:a32d1a85a830 | 380 | __nop(); |
RogerJKelly | 0:a32d1a85a830 | 381 | } |
RogerJKelly | 0:a32d1a85a830 | 382 | __gpo = 0; |
RogerJKelly | 0:a32d1a85a830 | 383 | for (; j < __oneLow; j++) { |
RogerJKelly | 0:a32d1a85a830 | 384 | __nop(); |
RogerJKelly | 0:a32d1a85a830 | 385 | } |
RogerJKelly | 0:a32d1a85a830 | 386 | } else { |
RogerJKelly | 0:a32d1a85a830 | 387 | __gpo = 1; |
RogerJKelly | 0:a32d1a85a830 | 388 | for (; j < __zeroHigh; j++) { |
RogerJKelly | 0:a32d1a85a830 | 389 | __nop(); |
RogerJKelly | 0:a32d1a85a830 | 390 | } |
RogerJKelly | 0:a32d1a85a830 | 391 | __gpo = 0; |
RogerJKelly | 0:a32d1a85a830 | 392 | for (; j < __zeroLow; j++) { |
RogerJKelly | 0:a32d1a85a830 | 393 | __nop(); |
RogerJKelly | 0:a32d1a85a830 | 394 | } |
RogerJKelly | 0:a32d1a85a830 | 395 | } |
RogerJKelly | 0:a32d1a85a830 | 396 | } |
RogerJKelly | 0:a32d1a85a830 | 397 | |
RogerJKelly | 0:a32d1a85a830 | 398 | // Exiting timing critical section, so enabling interrutps |
RogerJKelly | 0:a32d1a85a830 | 399 | __enable_irq(); |
RogerJKelly | 0:a32d1a85a830 | 400 | } |
RogerJKelly | 0:a32d1a85a830 | 401 |