├── Graph.ino └── Graphing.ino /Graph.ino: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | This program provides cartesian type graph function 4 | 5 | It requires and Arduino Mega (or UNO) and an Adafruit 3.5" TFT 320x480 + Touchscreen Breakout Board 6 | https://learn.adafruit.com/adafruit-3-5-color-320x480-tft-touchscreen-breakout/overview 7 | 8 | Adafruit libraries 9 | https://github.com/adafruit/Adafruit_HX8357_Library/archive/master.zip 10 | https://github.com/adafruit/Adafruit-GFX-Library/archive/master.zip 11 | 12 | optional touch screen libraries 13 | https://github.com/adafruit/Touch-Screen-Library/archive/master.zip 14 | 15 | Revisions 16 | rev date author description 17 | 1 12-24-2015 kasprzak initial creation 18 | 2 04-19-2024 kasprzak added example in loop for automatic rollover for continued data plotting--and fixed graph function to accomodate 19 | 20 | This pin setting will also operate the SD card 21 | 22 | Pin settings 23 | 24 | Arduino device 25 | 5V Vin 26 | GND GND 27 | A0 28 | A1 29 | A2 Y+ (for touch screen use) 30 | A3 X- (for touch screen use) 31 | A4 32 | A5 33 | 1 34 | 2 35 | 3 36 | 4 CCS (42 for mega) 37 | 5 38 | 6 39 | 7 Y- (44 for mega) 40 | 8 X+ (46 for mega) 41 | 9 DC (48 on mega * change define) 42 | 10 CS (53 for mega * change define) 43 | 11 MOSI (51 for mega) 44 | 12 MISO (50 for mega) 45 | 13 CLK (SCK) (52 for mega) 46 | 44 Y- (for touch screen only) 47 | 46 X+ (for touch screen only) 48 | 48 DC 49 | SDA 50 | SLC 51 | 52 | */ 53 | 54 | #include 55 | #include "Adafruit_HX8357.h" 56 | 57 | 58 | // These are 'flexible' lines that can be changed 59 | 60 | // for a nano 61 | #define TFT_CS 10 62 | #define TFT_DC 9 63 | 64 | 65 | #define LTBLUE 0xB6DF 66 | #define LTTEAL 0xBF5F 67 | #define LTGREEN 0xBFF7 68 | #define LTCYAN 0xC7FF 69 | #define LTRED 0xFD34 70 | #define LTMAGENTA 0xFD5F 71 | #define LTYELLOW 0xFFF8 72 | #define LTORANGE 0xFE73 73 | #define LTPINK 0xFDDF 74 | #define LTPURPLE 0xCCFF 75 | #define LTGREY 0xE71C 76 | 77 | #define BLUE 0x001F 78 | #define TEAL 0x0438 79 | #define GREEN 0x07E0 80 | #define CYAN 0x07FF 81 | #define RED 0xF800 82 | #define MAGENTA 0xF81F 83 | #define YELLOW 0xFFE0 84 | #define ORANGE 0xFC00 85 | #define PINK 0xF81F 86 | #define PURPLE 0x8010 87 | #define GREY 0xC618 88 | #define WHITE 0xFFFF 89 | #define BLACK 0x0000 90 | 91 | #define DKBLUE 0x000D 92 | #define DKTEAL 0x020C 93 | #define DKGREEN 0x03E0 94 | #define DKCYAN 0x03EF 95 | #define DKRED 0x6000 96 | #define DKMAGENTA 0x8008 97 | #define DKYELLOW 0x8400 98 | #define DKORANGE 0x8200 99 | #define DKPINK 0x9009 100 | #define DKPURPLE 0x4010 101 | #define DKGREY 0x4A49 102 | 103 | 104 | #define ADJ_PIN A0 105 | 106 | double a1, b1, c1, d1, r2, r1, vo, tempC, tempF, tempK; 107 | double x, y; 108 | double xLow = 0, xHigh = 60; 109 | Adafruit_HX8357 tft = Adafruit_HX8357(TFT_CS, TFT_DC); 110 | 111 | // this is the only external variable used by the graph 112 | // it's a flat to draw the coordinate system only on the first pass 113 | boolean display1 = true; 114 | boolean display2 = true; 115 | boolean display3 = true; 116 | boolean display4 = true; 117 | boolean display5 = true; 118 | boolean display6 = true; 119 | boolean display7 = true; 120 | boolean display8 = true; 121 | boolean display9 = true; 122 | double ox, oy; 123 | 124 | void setup() { 125 | 126 | Serial.begin(9600); 127 | 128 | pinMode(ADJ_PIN, INPUT); 129 | tft.begin(HX8357D); 130 | tft.fillScreen(BLACK); 131 | 132 | tft.setRotation(3); 133 | 134 | for (x = 0; x <= 6.3; x += .1) { 135 | 136 | y = sin(x); 137 | Graph(tft, x, y, 60, 290, 390, 260, 0, 6.5, 1, -1, 1, .25, "Sin Function - Large Graph", "x", "sin(x)", DKBLUE, RED, YELLOW, WHITE, BLACK, display1); 138 | } 139 | 140 | delay(5000); 141 | 142 | tft.fillScreen(BLACK); 143 | for (x = 0; x <= 6.3; x += .1) { 144 | 145 | y = sin(x); 146 | Graph(tft, x, y, 100, 280, 100, 240, 0, 6.5, 3.25, -1, 1, .25, "Sin Function - Narrow Graph", "x", "sin(x)", GREY, GREEN, RED, YELLOW, BLACK, display9); 147 | } 148 | 149 | delay(5000); 150 | 151 | tft.fillScreen(BLACK); 152 | for (x = 0; x <= 25.2; x += .1) { 153 | 154 | y = sin(x); 155 | Graph(tft, x, y, 50, 190, 400, 60, 0, 25, 5, -1, 1, .5, "Sin Function - Short Graph", "x", "sin(x)", DKYELLOW, YELLOW, GREEN, WHITE, BLACK, display8); 156 | } 157 | 158 | delay(5000); 159 | 160 | tft.fillScreen(BLACK); 161 | for (x = 0.001; x <= 10; x += .1) { 162 | 163 | y = log(x); 164 | Graph(tft, x, y, 50, 240, 300, 180, 0, 10, 1, -10, 5, 1, "Natural Log Function - Small Graph", "x", "ln(x)", BLUE, RED, WHITE, WHITE, BLACK, display2); 165 | } 166 | 167 | delay(5000); 168 | tft.fillScreen(BLACK); 169 | 170 | for (x = 0; x <= 10; x += 1) { 171 | 172 | y = x * x; 173 | Graph(tft, x, y, 50, 290, 390, 260, 0, 10, 1, 0, 100, 10, "Square Function", "x", "x^2", DKRED, RED, YELLOW, WHITE, BLACK, display3); 174 | } 175 | 176 | delay(5000); 177 | tft.fillScreen(BLACK); 178 | 179 | for (x = 0.00; x <= 20; x += .01) { 180 | 181 | y = ((sin(x)) * x + cos(x)) - log(x); 182 | Graph(tft, x, y, 50, 290, 390, 260, 0, 20, 1, -20, 20, 5, "Weird Function", "x", " y = sin(x) + cos(x) - log(x)", ORANGE, YELLOW, CYAN, WHITE, BLACK, display4); 183 | } 184 | 185 | delay(5000); 186 | tft.fillScreen(BLACK); 187 | 188 | tft.setRotation(2); 189 | for (x = 0; x <= 12.6; x += .1) { 190 | 191 | y = sin(x); 192 | Graph(tft, x, y, 50, 250, 150, 150, 0, 13, 3.5, -1, 1, 1, "Sin(x)", "x", "sin(x)", DKBLUE, RED, YELLOW, WHITE, BLACK, display5); 193 | } 194 | 195 | tft.setRotation(3); 196 | delay(5000); 197 | tft.fillScreen(WHITE); 198 | 199 | for (x = 0; x <= 6.3; x += .05) { 200 | 201 | y = cos(x); 202 | Graph(tft, x, y, 100, 250, 300, 200, 0, 6.5, 3.25, -1, 1, 1, "Cos Function", "x", "cos(x)", DKGREY, GREEN, BLUE, BLACK, WHITE, display6); 203 | } 204 | 205 | delay(5000); 206 | tft.fillScreen(BLACK); 207 | } 208 | 209 | 210 | void loop(void) { 211 | 212 | x++; 213 | y = analogRead(ADJ_PIN) / 204.6; 214 | Graph(tft, x, y, 50, 290, 390, 260, xLow, xHigh, 10, 0, 5, 1, "A0 Input", " Time [s]", "Volts", DKBLUE, RED, GREEN, WHITE, BLACK, display7); 215 | delay(250); 216 | 217 | if (x >= xHigh) { 218 | //x = 0; 219 | xLow += 60; 220 | xHigh += 60; 221 | display7 = true; 222 | tft.fillScreen(BLACK); 223 | } 224 | } 225 | 226 | /* 227 | 228 | function to draw a cartesian coordinate system and plot whatever data you want 229 | just pass x and y and the graph will be drawn 230 | 231 | huge arguement list 232 | &d name of your display object 233 | x = x data point 234 | y = y datapont 235 | gx = x graph location (lower left) 236 | gy = y graph location (lower left) 237 | w = width of graph 238 | h = height of graph 239 | xlo = lower bound of x axis 240 | xhi = upper bound of x asis 241 | xinc = division of x axis (distance not count) 242 | ylo = lower bound of y axis 243 | yhi = upper bound of y asis 244 | yinc = division of y axis (distance not count) 245 | title = title of graph 246 | xlabel = x asis label 247 | ylabel = y asis label 248 | gcolor = graph line colors 249 | acolor = axi ine colors 250 | pcolor = color of your plotted data 251 | tcolor = text color 252 | bcolor = background color 253 | &redraw = flag to redraw graph on fist call only 254 | */ 255 | 256 | 257 | void Graph(Adafruit_HX8357 &d, double x, double y, double gx, double gy, double w, double h, double xlo, double xhi, double xinc, double ylo, double yhi, double yinc, String title, String xlabel, String ylabel, unsigned int gcolor, unsigned int acolor, unsigned int pcolor, unsigned int tcolor, unsigned int bcolor, boolean &redraw) { 258 | 259 | double ydiv, xdiv; 260 | // initialize old x and old y in order to draw the first point of the graph 261 | // but save the transformed value 262 | // note my transform funcition is the same as the map function, except the map uses long and we need doubles 263 | //static double ox = (x - xlo) * ( w) / (xhi - xlo) + gx; 264 | //static double oy = (y - ylo) * (gy - h - gy) / (yhi - ylo) + gy; 265 | double i; 266 | double temp; 267 | int rot, newrot; 268 | 269 | if (redraw == true) { 270 | 271 | redraw = false; 272 | ox = (x - xlo) * (w) / (xhi - xlo) + gx; 273 | oy = (y - ylo) * (gy - h - gy) / (yhi - ylo) + gy; 274 | // draw y scale 275 | for (i = ylo; i <= yhi; i += yinc) { 276 | // compute the transform 277 | temp = (i - ylo) * (gy - h - gy) / (yhi - ylo) + gy; 278 | 279 | if (i == ylo) { 280 | d.drawLine(gx, temp, gx + w, temp, acolor); 281 | } else { 282 | d.drawLine(gx, temp, gx + w, temp, gcolor); 283 | } 284 | 285 | d.setTextSize(1); 286 | d.setTextColor(tcolor, bcolor); 287 | d.setCursor(gx - 30, temp); 288 | // precision is default Arduino--this could really use some format control 289 | d.println(i); 290 | } 291 | // draw x scale 292 | for (i = xlo; i <= xhi; i += xinc) { 293 | 294 | // compute the transform 295 | 296 | temp = (i - xlo) * (w) / (xhi - xlo) + gx; 297 | if (i == xlo) { 298 | d.drawLine(temp, gy, temp, gy - h, acolor); 299 | } else { 300 | d.drawLine(temp, gy, temp, gy - h, gcolor); 301 | } 302 | 303 | d.setTextSize(1); 304 | d.setTextColor(tcolor, bcolor); 305 | d.setCursor(temp, gy + 10); 306 | // precision is default Arduino--this could really use some format control 307 | d.println(i); 308 | } 309 | 310 | //now draw the labels 311 | d.setTextSize(2); 312 | d.setTextColor(tcolor, bcolor); 313 | d.setCursor(gx, gy - h - 30); 314 | d.println(title); 315 | 316 | d.setTextSize(1); 317 | d.setTextColor(acolor, bcolor); 318 | d.setCursor(gx, gy + 20); 319 | d.println(xlabel); 320 | 321 | /* 322 | // some day auto rotate 323 | d.setTextSize(1); 324 | 325 | d.setTextColor(acolor, bcolor); 326 | d.setCursor(gy - h - 10, gx-40); 327 | d.println(ylabel); 328 | */ 329 | } 330 | 331 | //graph drawn now plot the data 332 | // the entire plotting code are these few lines... 333 | // recall that ox and oy are initialized as static above 334 | x = (x - xlo) * (w) / (xhi - xlo) + gx; 335 | y = (y - ylo) * (gy - h - gy) / (yhi - ylo) + gy; 336 | d.drawLine(ox, oy, x, y, pcolor); 337 | d.drawLine(ox, oy + 1, x, y + 1, pcolor); 338 | d.drawLine(ox, oy - 1, x, y - 1, pcolor); 339 | ox = x; 340 | oy = y; 341 | } 342 | 343 | /* 344 | End of graphing functioin 345 | */ 346 | -------------------------------------------------------------------------------- /Graphing.ino: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | This program provides bar graph (horizontal and vertical orientations) and a dial type graph functions 4 | 5 | It requires and Arduino Mega (or UNO) and an Adafruit 3.5" TFT 320x480 + Touchscreen Breakout Board 6 | https://learn.adafruit.com/adafruit-3-5-color-320x480-tft-touchscreen-breakout/overview 7 | 8 | Adafruit libraries 9 | https://github.com/adafruit/Adafruit_HX8357_Library/archive/master.zip 10 | https://github.com/adafruit/Adafruit-GFX-Library/archive/master.zip 11 | 12 | optional touch screen libraries 13 | https://github.com/adafruit/Touch-Screen-Library/archive/master.zip 14 | 15 | Revisions 16 | rev date author description 17 | 1 12-19-2015 kasprzak initial creation 18 | 19 | 20 | This pin setting will also operate the SD card 21 | 22 | Pin settings 23 | 24 | Arduino device 25 | 5V Vin 26 | GND GND 27 | A0 28 | A1 29 | A2 Y+ (for touch screen use) 30 | A3 X- (for touch screen use) 31 | A4 32 | A5 33 | 1 34 | 2 35 | 3 36 | 4 CCS (42 for mega) 37 | 5 38 | 6 39 | 7 Y- (44 for mega) 40 | 8 X+ (46 for mega) 41 | 9 DC (48 on mega * change define) 42 | 10 CS (53 for mega * change define) 43 | 11 MOSI (51 for mega) 44 | 12 MISO (50 for mega) 45 | 13 CLK (SCK) (52 for mega) 46 | 44 Y- (for touch screen only) 47 | 46 X+ (for touch screen only) 48 | 48 DC 49 | SDA 50 | SLC 51 | 52 | */ 53 | 54 | 55 | #include 56 | #include 57 | 58 | // http://www.barth-dev.de/online/rgb565-color-picker/ 59 | #define LTBLUE 0xB6DF 60 | #define LTTEAL 0xBF5F 61 | #define LTGREEN 0xBFF7 62 | #define LTCYAN 0xC7FF 63 | #define LTRED 0xFD34 64 | #define LTMAGENTA 0xFD5F 65 | #define LTYELLOW 0xFFF8 66 | #define LTORANGE 0xFE73 67 | #define LTPINK 0xFDDF 68 | #define LTPURPLE 0xCCFF 69 | #define LTGREY 0xE71C 70 | 71 | #define BLUE 0x001F 72 | #define TEAL 0x0438 73 | #define GREEN 0x07E0 74 | #define CYAN 0x07FF 75 | #define RED 0xF800 76 | #define MAGENTA 0xF81F 77 | #define YELLOW 0xFFE0 78 | #define ORANGE 0xFD20 79 | #define PINK 0xF81F 80 | #define PURPLE 0x801F 81 | #define GREY 0xC618 82 | #define WHITE 0xFFFF 83 | #define BLACK 0x0000 84 | 85 | #define DKBLUE 0x000D 86 | #define DKTEAL 0x020C 87 | #define DKGREEN 0x03E0 88 | #define DKCYAN 0x03EF 89 | #define DKRED 0x6000 90 | #define DKMAGENTA 0x8008 91 | #define DKYELLOW 0x8400 92 | #define DKORANGE 0x8200 93 | #define DKPINK 0x9009 94 | #define DKPURPLE 0x4010 95 | #define DKGREY 0x4A49 96 | 97 | #define TFT_CS 53 98 | #define TFT_DC 48 99 | #define ADJ_PIN A0 100 | 101 | double volts; 102 | double bvolts; 103 | double pmvolts; 104 | 105 | boolean graph_1 = true; 106 | boolean graph_2 = true; 107 | boolean graph_3 = true; 108 | boolean graph_4 = true; 109 | boolean graph_5 = true; 110 | boolean graph_6 = true; 111 | boolean graph_7 = true; 112 | 113 | Adafruit_HX8357 tft = Adafruit_HX8357(TFT_CS, TFT_DC); 114 | 115 | void setup() { 116 | Serial.begin(9600); 117 | tft.begin(HX8357D); 118 | tft.fillScreen(BLACK); 119 | tft.setRotation(3); 120 | pinMode(A0, INPUT); 121 | } 122 | 123 | void loop(void) { 124 | 125 | bvolts = analogRead(A0); 126 | volts = (bvolts / 204.6 ) ; 127 | pmvolts = (bvolts / 204.6 ) - 2.5 ; 128 | 129 | DrawBarChartV(tft, 10, 290, 30, 260, 0, 1200 , 100, bvolts , 4 , 0, BLUE, DKBLUE, BLUE, WHITE, BLACK, "Bits", graph_1); 130 | 131 | DrawBarChartH(tft, 100, 250, 300, 30, -2.5, 2.5, .5, pmvolts, 2, 1, GREEN, DKGREEN, GREEN, WHITE, BLACK, "Offset", graph_6); 132 | 133 | DrawDial(tft, 260, 120, 110, 0, 5 , 1, 240, volts, 1 , 2, RED, WHITE, BLACK, "Volts", graph_7); 134 | 135 | } 136 | 137 | 138 | /* 139 | This method will draw a vertical bar graph for single input 140 | it has a rather large arguement list and is as follows 141 | 142 | &d = display object name 143 | x = position of bar graph (lower left of bar) 144 | y = position of bar (lower left of bar 145 | w = width of bar graph 146 | h = height of bar graph (does not need to be the same as the max scale) 147 | loval = lower value of the scale (can be negative) 148 | hival = upper value of the scale 149 | inc = scale division between loval and hival 150 | curval = date to graph (must be between loval and hival) 151 | dig = format control to set number of digits to display (not includeing the decimal) 152 | dec = format control to set number of decimals to display (not includeing the decimal) 153 | barcolor = color of bar graph 154 | voidcolor = color of bar graph background 155 | bordercolor = color of the border of the graph 156 | textcolor = color of the text 157 | backcolor = color of the bar graph's background 158 | label = bottom lable text for the graph 159 | redraw = flag to redraw display only on first pass (to reduce flickering) 160 | 161 | */ 162 | 163 | void DrawBarChartV(Adafruit_HX8357 & d, double x , double y , double w, double h , double loval , double hival , double inc , double curval , int dig , int dec, unsigned int barcolor, unsigned int voidcolor, unsigned int bordercolor, unsigned int textcolor, unsigned int backcolor, String label, boolean & redraw) 164 | { 165 | 166 | double stepval, range; 167 | double my, level; 168 | double i, data; 169 | // draw the border, scale, and label once 170 | // avoid doing this on every update to minimize flicker 171 | if (redraw == true) { 172 | redraw = false; 173 | 174 | d.drawRect(x - 1, y - h - 1, w + 2, h + 2, bordercolor); 175 | d.setTextColor(textcolor, backcolor); 176 | d.setTextSize(2); 177 | d.setCursor(x , y + 10); 178 | d.println(label); 179 | // step val basically scales the hival and low val to the height 180 | // deducting a small value to eliminate round off errors 181 | // this val may need to be adjusted 182 | stepval = ( inc) * (double (h) / (double (hival - loval))) - .001; 183 | for (i = 0; i <= h; i += stepval) { 184 | my = y - h + i; 185 | d.drawFastHLine(x + w + 1, my, 5, textcolor); 186 | // draw lables 187 | d.setTextSize(1); 188 | d.setTextColor(textcolor, backcolor); 189 | d.setCursor(x + w + 12, my - 3 ); 190 | data = hival - ( i * (inc / stepval)); 191 | d.println(Format(data, dig, dec)); 192 | } 193 | } 194 | // compute level of bar graph that is scaled to the height and the hi and low vals 195 | // this is needed to accompdate for +/- range 196 | level = (h * (((curval - loval) / (hival - loval)))); 197 | // draw the bar graph 198 | // write a upper and lower bar to minimize flicker cause by blanking out bar and redraw on update 199 | d.fillRect(x, y - h, w, h - level, voidcolor); 200 | d.fillRect(x, y - level, w, level, barcolor); 201 | // write the current value 202 | d.setTextColor(textcolor, backcolor); 203 | d.setTextSize(2); 204 | d.setCursor(x , y - h - 23); 205 | d.println(Format(curval, dig, dec)); 206 | 207 | } 208 | 209 | /* 210 | This method will draw a dial-type graph for single input 211 | it has a rather large arguement list and is as follows 212 | 213 | &d = display object name 214 | cx = center position of dial 215 | cy = center position of dial 216 | r = radius of the dial 217 | loval = lower value of the scale (can be negative) 218 | hival = upper value of the scale 219 | inc = scale division between loval and hival 220 | sa = sweep angle for the dials scale 221 | curval = date to graph (must be between loval and hival) 222 | dig = format control to set number of digits to display (not includeing the decimal) 223 | dec = format control to set number of decimals to display (not includeing the decimal) 224 | needlecolor = color of the needle 225 | dialcolor = color of the dial 226 | textcolor = color of all text (background is dialcolor) 227 | label = bottom lable text for the graph 228 | redraw = flag to redraw display only on first pass (to reduce flickering) 229 | */ 230 | 231 | void DrawDial(Adafruit_HX8357 & d, int cx, int cy, int r, double loval , double hival , double inc, double sa, double curval, int dig , int dec, unsigned int needlecolor, unsigned int dialcolor, unsigned int textcolor, String label, boolean & redraw) { 232 | 233 | double ix, iy, ox, oy, tx, ty, lx, rx, ly, ry, i, offset, stepval, data, angle; 234 | double degtorad = .0174532778; 235 | static double px = cx, py = cy, pix = cx, piy = cy, plx = cx, ply = cy, prx = cx, pry = cy; 236 | 237 | // draw the dial only one time--this will minimize flicker 238 | if ( redraw == true) { 239 | redraw = false; 240 | d.fillCircle(cx, cy, r - 2, dialcolor); 241 | d.drawCircle(cx, cy, r, needlecolor); 242 | d.drawCircle(cx, cy, r - 1, needlecolor); 243 | d.setTextColor(textcolor, dialcolor); 244 | d.setTextSize(2); 245 | d.setCursor(cx - 25, cy + 40); 246 | d.println(label); 247 | 248 | } 249 | // draw the current value 250 | d.setTextSize(2); 251 | d.setTextColor(textcolor, dialcolor); 252 | d.setCursor(cx - 25, cy + 20 ); 253 | d.println(Format(curval, dig, dec)); 254 | // center the scale about the vertical axis--and use this to offset the needle, and scale text 255 | offset = (270 + sa / 2) * degtorad; 256 | // find hte scale step value based on the hival low val and the scale sweep angle 257 | // deducting a small value to eliminate round off errors 258 | // this val may need to be adjusted 259 | stepval = ( inc) * (double (sa) / (double (hival - loval))) + .00; 260 | // draw the scale and numbers 261 | // note draw this each time to repaint where the needle was 262 | for (i = 0; i <= sa; i += stepval) { 263 | angle = ( i * degtorad); 264 | angle = offset - angle ; 265 | ox = (r - 2) * cos(angle) + cx; 266 | oy = (r - 2) * sin(angle) + cy; 267 | ix = (r - 10) * cos(angle) + cx; 268 | iy = (r - 10) * sin(angle) + cy; 269 | tx = (r - 30) * cos(angle) + cx; 270 | ty = (r - 30) * sin(angle) + cy; 271 | d.drawLine(ox, oy, ix, iy, textcolor); 272 | d.setTextSize(1.5); 273 | d.setTextColor(textcolor, dialcolor); 274 | d.setCursor(tx - 10, ty ); 275 | data = hival - ( i * (inc / stepval)) ; 276 | d.println(Format(data, dig, dec)); 277 | } 278 | // compute and draw the needle 279 | angle = (sa * (1 - (((curval - loval) / (hival - loval))))); 280 | angle = angle * degtorad; 281 | angle = offset - angle ; 282 | ix = (r - 10) * cos(angle) + cx; 283 | iy = (r - 10) * sin(angle) + cy; 284 | // draw a triangle for the needle (compute and store 3 vertiticies) 285 | lx = 5 * cos(angle - 90 * degtorad) + cx; 286 | ly = 5 * sin(angle - 90 * degtorad) + cy; 287 | rx = 5 * cos(angle + 90 * degtorad) + cx; 288 | ry = 5 * sin(angle + 90 * degtorad) + cy; 289 | // first draw the previous needle in dial color to hide it 290 | // note draw performance for triangle is pretty bad... 291 | 292 | //d.fillTriangle (pix, piy, plx, ply, prx, pry, dialcolor); 293 | //d.fillTriangle (pix, piy, plx, ply, prx, pry, dialcolor); 294 | 295 | //d.fillTriangle (pix, piy, plx, ply, prx - 20, pry - 20, dialcolor); 296 | //d.fillTriangle (pix, piy, prx, pry, prx + 20, pry + 20, dialcolor); 297 | 298 | d.fillTriangle (pix, piy, plx, ply, prx, pry, dialcolor); 299 | d.drawTriangle (pix, piy, plx, ply, prx, pry, dialcolor); 300 | 301 | // then draw the old needle in need color to display it 302 | d.fillTriangle (ix, iy, lx, ly, rx, ry, needlecolor); 303 | d.drawTriangle (ix, iy, lx, ly, rx, ry, textcolor); 304 | 305 | // draw a cute little dial center 306 | d.fillCircle(cx, cy, 8, textcolor); 307 | //save all current to old so the previous dial can be hidden 308 | pix = ix; 309 | piy = iy; 310 | plx = lx; 311 | ply = ly; 312 | prx = rx; 313 | pry = ry; 314 | 315 | } 316 | 317 | /* 318 | This method will draw a horizontal bar graph for single input 319 | it has a rather large arguement list and is as follows 320 | 321 | &d = display object name 322 | x = position of bar graph (upper left of bar) 323 | y = position of bar (upper left of bar (add some vale to leave room for label) 324 | w = width of bar graph (does not need to be the same as the max scale) 325 | h = height of bar graph 326 | loval = lower value of the scale (can be negative) 327 | hival = upper value of the scale 328 | inc = scale division between loval and hival 329 | curval = date to graph (must be between loval and hival) 330 | dig = format control to set number of digits to display (not includeing the decimal) 331 | dec = format control to set number of decimals to display (not includeing the decimal) 332 | barcolor = color of bar graph 333 | voidcolor = color of bar graph background 334 | bordercolor = color of the border of the graph 335 | textcolor = color of the text 336 | back color = color of the bar graph's background 337 | label = bottom lable text for the graph 338 | redraw = flag to redraw display only on first pass (to reduce flickering) 339 | */ 340 | 341 | void DrawBarChartH(Adafruit_HX8357 & d, double x , double y , double w, double h , double loval , double hival , double inc , double curval , int dig , int dec, unsigned int barcolor, unsigned int voidcolor, unsigned int bordercolor, unsigned int textcolor, unsigned int backcolor, String label, boolean & redraw) 342 | { 343 | double stepval, range; 344 | double mx, level; 345 | double i, data; 346 | 347 | // draw the border, scale, and label once 348 | // avoid doing this on every update to minimize flicker 349 | // draw the border and scale 350 | if (redraw == true) { 351 | redraw = false; 352 | d.drawRect(x , y , w, h, bordercolor); 353 | d.setTextColor(textcolor, backcolor); 354 | d.setTextSize(2); 355 | d.setCursor(x , y - 20); 356 | d.println(label); 357 | // step val basically scales the hival and low val to the width 358 | stepval = inc * (double (w) / (double (hival - loval))) - .00001; 359 | // draw the text 360 | for (i = 0; i <= w; i += stepval) { 361 | d.drawFastVLine(i + x , y + h + 1, 5, textcolor); 362 | // draw lables 363 | d.setTextSize(1); 364 | d.setTextColor(textcolor, backcolor); 365 | d.setCursor(i + x , y + h + 10); 366 | // addling a small value to eliminate round off errors 367 | // this val may need to be adjusted 368 | data = ( i * (inc / stepval)) + loval + 0.00001; 369 | d.println(Format(data, dig, dec)); 370 | } 371 | } 372 | // compute level of bar graph that is scaled to the width and the hi and low vals 373 | // this is needed to accompdate for +/- range capability 374 | // draw the bar graph 375 | // write a upper and lower bar to minimize flicker cause by blanking out bar and redraw on update 376 | level = (w * (((curval - loval) / (hival - loval)))); 377 | d.fillRect(x + level + 1, y + 1, w - level - 2, h - 2, voidcolor); 378 | d.fillRect(x + 1, y + 1 , level - 1, h - 2, barcolor); 379 | // write the current value 380 | d.setTextColor(textcolor, backcolor); 381 | d.setTextSize(2); 382 | d.setCursor(x + w + 10 , y + 5); 383 | d.println(Format(curval, dig, dec)); 384 | } 385 | 386 | 387 | String Format(double val, int dec, int dig ) { 388 | int addpad = 0; 389 | char sbuf[20]; 390 | String condata = (dtostrf(val, dec, dig, sbuf)); 391 | 392 | 393 | int slen = condata.length(); 394 | for ( addpad = 1; addpad <= dec + dig - slen; addpad++) { 395 | condata = " " + condata; 396 | } 397 | return (condata); 398 | 399 | } 400 | 401 | --------------------------------------------------------------------------------