راه اندازی نمایشگر LCD رنگی 3.2 اینچ آردوینو Mega
LCD چیست:
مخفف عبارت “Liquid Crystal Display” به معنای صفحه نمایش کریستال مایع است. کریستالهای مایع موادی هستند که ظاهر مایع دارند، اما مولکولهای آنها آرایش خاصی نسبت به یکدیگر دارند. به همین دلیل کریستال مایع خصوصیاتی شبیه به مایع و جامد داشته و به همین دلیل با چنین اسم متناقضی خوانده میشوند. این مواد به شدت به دما حساس اند و اندکی حرارت لازم است تا آنها را به مایع واقعی درآورد و یا اندکی سرما تا به حالت معمولی تبدیل شود. انواع مختلفی از مواد شناخته شدهاند که در دمای معمولی چنین خصوصیاتی دارند. اما دستهای از آنهاهستند که به جریان الکتریسیته هم حساس هستند و مولکولهای آن متناسب با ولتاژ اعمالی تغییر زاویه میدهند. این خصوصیت عجیب اثر جالبی هم دارد. وقتی نور از درون یک کریستال مایع این چنین عبور کند، پلاریزاسیون یا قطب آن هم جهت با مولکولهایهای کریستال میشود. با این توضیح که چون کریستالهای مایع شفاف و هادی الکتریسیته هستند، به راحتی میتوان آنها را در جریان الکتریسیته قرار داد و نور را از آن عبور داد. برای این کار به جز کریستال مایع به ۲ تکه از این شیشه پلاروید یا قطبشگر هم نیاز است. اگر دو تکه از این شیشهها را روی هم قرار داده شود. نور به راحتی از آن عبور میکند. اما وقتی یکی از آنها را ۹۰ درجه نسبت به دیگری بچرخانید، دیگر نور رد نمیشود. این اتفاق به این دلیل روی میدهد که هر شیشه نو را فقط در جهت خاص محور خود عبور میدهد. اگر دو شیشه هم محور باشند نور به راحتی عبور میکند اما اگر محورها با هم زاویه ۹۰ درجه داشته باشند نور رد نخواهد شد.
ذرات و مولکولهای کریستال مایع در میان صفحات شیشهای پلاریزه شده و فیلترهای LCD در تلویزیون رنگی قرار دارند. همچنین یک لایه الکترود بسیار باریک کار تحریک کریستال مایع را بر عهده دارد. نور پس واقع در پشت CCFL) Cold Cathode Fluorescence Lamp) یا Light Emitting Diode (همان LED) زمینه سفید توسط یک لامپ ولتاژ بالا ایجاد شده و بوسیله یک منعکس کننده، شدت یکسانی پیدا میکند. نور سفید بعد از عبور از لایه LCD صفحه اول شیشه پلاریزه میشود. اختلاف پتانسیل خاصی نورهای اصلی مو جود در نور سفید را جهت میدهد و بعد از عبور از فیلترهای آبی، سبز و قرمز اگر نور حاصل در راستای جهت پلاریزه شیشه دوم بود از آن عبور میکند.
برای ساخت LCD دو شیشه پلاروید را با ۹۰ درجه اختلاف نسبت به یکدیگر قرار میدهند و یک کریستال مایع بین آنها میگذارند. وقتی کریستال به جریان برق وصل نباشد؛ نور از قطبشگر اول میگذرد و وارد کریستال مایع میشود جهتش ۹۰ درجه تغییر کرده و به همین دلیل از قطبشگر دوم هم عبور کرده و به چشم میرسد. اما وقتی که جریان به کریستال وصل باشد، نور دیگر چرخشی نخواهد داشت و نمیتواند از کریستال دوم عبور کند. ساختن یک LCD همانطور که در بالا توضیح داده شد، بسیار سادهتر از آن است که به نظر میآید. فقط به یک ساندویچ شیشه و کریستال نیاز داریم. اما همین ساندویچ ساده ۸۰ سال پس از کشف کریستالهای مایع ساخته شد. کریستال مایع را یک گیاهشناس اتریشی در سال ۱۸۸۸ برای اولین بار در حین ذوب جامدی از مشتقات آلی کشف کرد. اما اولین LCD را یک کارخانه آمریکایی در سال ۱۹۶۸ ساخت. تکنولوژی ساخت LCD هر روز متکامل تر شده و جای بیشتری در صنایع امروز به خود اختصاص میدهد. البته هنوز هم تحقیقات برای ساخت نمونههای بهتر و کاراتر این وسیله ادامه دارد.
ویدیوی راه اندازی نمایشگر LCD رنگی 3.2 اینچ آردوینوMega
مشخصات نمایشگر LCD رنگی 3.2 اینچ آردوینو Mega
– نمایشگر LCD رنگی با رزولوشن 480*320
– قالبیت نصب بر روی برد آردوینو مگا
– دارای درایور نمایشگر ILI9481
– دارای اسلات MMC/SD برای راه اندازی SD کارت
برنامه راه اندازی نمایشگر LCD رنگی 3.2 اینچ آردوینوMega
دانلود برنامه و کتابخانه آردوینو
/* An example showing 'ring' analogue meters on a HX8357 TFT colour screen Needs Fonts 2, 4 and 7 (also Font 6 if using a large size meter) */ // Meter colour schemes #define RED2RED 0 #define GREEN2GREEN 1 #define BLUE2BLUE 2 #define BLUE2RED 3 #define GREEN2RED 4 #define RED2GREEN 5 #include <Adafruit_GFX_AS.h> // Core graphics library #include <Adafruit_HX8357_AS.h> // Fast hardware-specific library #define HX8357_GREY 0x2104 // Dark grey 16 bit colour Adafruit_HX8357_AS tft = Adafruit_HX8357_AS(); // Invoke custom library uint32_t runTime = -99999; // time for next update int reading = 0; // Value to be displayed int d = 0; // Variable used for the sinewave test waveform boolean alert = 0; int8_t ramp = 1; void setup(void) { tft.begin(HX8357B); //Serial.begin(9600); tft.setRotation(1); tft.fillScreen(HX8357_BLACK); } void loop() { if (millis() - runTime >= 0L) { // Execute every 2s runTime = millis(); // Test with a slowly changing value from a Sine function //d += 4; if (d >= 360) d = 0; // Set the the position, gap between meters, and inner radius of the meters int xpos = 0, ypos = 5, gap = 4, radius = 52; // Draw meter and get back x position of next meter // Test with Sine wave function, normally reading will be from a sensor //reading = 250 + 250 * sineWave(d+0); //xpos = gap + ringMeter(reading, 0, 500, xpos, ypos, radius, "mA", GREEN2RED); // Draw analogue meter //reading = 20 + 30 * sineWave(d+60); //xpos = gap + ringMeter(reading, -10, 50, xpos, ypos, radius, "degC", BLUE2RED); // Draw analogue meter //reading = 50 + 50 * sineWave(d + 120); //ringMeter(reading, 0, 100, xpos, ypos, radius, "%RH", BLUE2BLUE); // Draw analogue meter // Draw two more larger meters //xpos = 20, ypos = 115, gap = 24, radius = 64; //reading = 1000 + 150 * sineWave(d + 90); //xpos = gap + ringMeter(reading, 850, 1150, xpos, ypos, radius, "mb", BLUE2RED); // Draw analogue meter //reading = 15 + 15 * sineWave(d + 150); //xpos = gap + ringMeter(reading, 0, 30, xpos, ypos, radius, "Volts", GREEN2GREEN); // Draw analogue meter // Draw a large meter xpos = 480/2 - 160, ypos = 0, gap = 15, radius = 170; reading +=(ramp); if (reading>98) ramp = -1; if (reading<0) ramp = 1; // Comment out above meters, then uncomment the next line to show large meter ringMeter(reading,0,100, xpos,ypos,radius," Watts",GREEN2RED); // Draw analogue meter } } // ######################################################################### // Draw the meter on the screen, returns x coord of righthand side // ######################################################################### int ringMeter(int value, int vmin, int vmax, int x, int y, int r, char *units, byte scheme) { // Minimum value of r is about 52 before value text intrudes on ring // drawing the text first is an option x += r; y += r; // Calculate coords of centre of ring int w = r / 3; // Width of outer ring is 1/4 of radius int angle = 150; // Half the sweep angle of meter (300 degrees) int v = map(value, vmin, vmax, -angle, angle); // Map the value to an angle v byte seg = 3; // Segments are 3 degrees wide = 100 segments for 300 degrees byte inc = 6; // Draw segments every 3 degrees, increase to 6 for segmented ring // Variable to save "value" text colour from scheme and set default int colour = HX8357_BLUE; // Draw colour blocks every inc degrees for (int i = -angle+inc/2; i < angle-inc/2; i += inc) { // Calculate pair of coordinates for segment start float sx = cos((i - 90) * 0.0174532925); float sy = sin((i - 90) * 0.0174532925); uint16_t x0 = sx * (r - w) + x; uint16_t y0 = sy * (r - w) + y; uint16_t x1 = sx * r + x; uint16_t y1 = sy * r + y; // Calculate pair of coordinates for segment end float sx2 = cos((i + seg - 90) * 0.0174532925); float sy2 = sin((i + seg - 90) * 0.0174532925); int x2 = sx2 * (r - w) + x; int y2 = sy2 * (r - w) + y; int x3 = sx2 * r + x; int y3 = sy2 * r + y; if (i < v) { // Fill in coloured segments with 2 triangles switch (scheme) { case 0: colour = HX8357_RED; break; // Fixed colour case 1: colour = HX8357_GREEN; break; // Fixed colour case 2: colour = HX8357_BLUE; break; // Fixed colour case 3: colour = rainbow(map(i, -angle, angle, 0, 127)); break; // Full spectrum blue to red case 4: colour = rainbow(map(i, -angle, angle, 70, 127)); break; // Green to red (high temperature etc) case 5: colour = rainbow(map(i, -angle, angle, 127, 63)); break; // Red to green (low battery etc) default: colour = HX8357_BLUE; break; // Fixed colour } tft.fillTriangle(x0, y0, x1, y1, x2, y2, colour); tft.fillTriangle(x1, y1, x2, y2, x3, y3, colour); //text_colour = colour; // Save the last colour drawn } else // Fill in blank segments { tft.fillTriangle(x0, y0, x1, y1, x2, y2, HX8357_GREY); tft.fillTriangle(x1, y1, x2, y2, x3, y3, HX8357_GREY); } } // Convert value to a string char buf[10]; byte len = 3; if (value > 999) len = 5; dtostrf(value, len, 0, buf); buf[len] = ' '; buf[len+1] = 0; // Add blanking space and terminator, helps to centre text too! // Set the text colour to default tft.setTextSize(2); if (value<vmin || value>vmax) { drawAlert(x,y+90,50,1); } else { drawAlert(x,y+90,50,0); } tft.setTextColor(HX8357_WHITE, HX8357_BLACK); // Uncomment next line to set the text colour to the last segment value! tft.setTextColor(colour, HX8357_BLACK); // Print value, if the meter is large then use big font 6, othewise use 4 if (r > 84) tft.drawRightString(buf, x + 96, y - 60, 7); // Value in middle else tft.drawCentreString(buf, x - 5, y - 20, 4); // Value in middle tft.setTextSize(1); // Print units, if the meter is large then use big font 4, othewise use 2 tft.setTextColor(HX8357_WHITE, HX8357_BLACK); if (r > 84) tft.drawCentreString(units, x, y + 50, 4); // Units display else tft.drawCentreString(units, x, y + 5, 2); // Units display // Calculate and return right hand side x coordinate return x + r; } void drawAlert(int x, int y , int side, boolean draw) { if (draw && !alert) { tft.fillTriangle(x, y, x+30, y+47, x-30, y+47, rainbow(95)); tft.setTextColor(HX8357_BLACK); tft.drawCentreString("!", x, y + 6, 4); alert = 1; } else if (!draw) { tft.fillTriangle(x, y, x+30, y+47, x-30, y+47, HX8357_BLACK); alert = 0; } } // ######################################################################### // Return a 16 bit rainbow colour // ######################################################################### unsigned int rainbow(byte value) { // Value is expected to be in range 0-127 // The value is converted to a spectrum colour from 0 = blue through to 127 = red byte red = 0; // Red is the top 5 bits of a 16 bit colour value byte green = 0;// Green is the middle 6 bits byte blue = 0; // Blue is the bottom 5 bits byte quadrant = value / 32; if (quadrant == 0) { blue = 31; green = 2 * (value % 32); red = 0; } if (quadrant == 1) { blue = 31 - (value % 32); green = 63; red = 0; } if (quadrant == 2) { blue = 0; green = 63; red = value % 32; } if (quadrant == 3) { blue = 0; green = 63 - 2 * (value % 32); red = 31; } return (red << 11) + (green << 5) + blue; } // ######################################################################### // Return a value in range -1 to +1 for a given phase angle in degrees // ######################################################################### float sineWave(int phase) { return sin(phase * 0.0174532925); }