예전 글(http://deneb21.tistory.com/508) 에서 노키아 5110 LCD를 아두이노로 컨트롤 하는 방법에 대해서 알아보았다. 이번에는 그래픽 라이브러리를 사용해서 간단한 그래픽을 나타내 보려고 한다. 라이브러리는 Adafruit 의 GFX 라이브러리와 PCD8544(5110 LCD 정식 품명) 라이브러리를 이용했으며 다운 받은 라이브러리에 포함된 예제를 핀배열과 백라이트 부분을 살짝 수정해서 그래픽을 표시해 보았다. 5110 LCD에 대한 기본적인 사항은 이 글의 첫 줄에 있는 예전 글을 참고하면 된다.
연결은 예전과 동일하다. 만약 라이브러리 파일의 예제 그대로 연결하고 싶다면 아래의 연결을 따르지 않아도 된다. 물론 아래의 소스도 수정이 되어야 할 것이다.
■ Nokia 5110 LCD 와 아두이노 우노의 연결
Arduino UNO Nokia 5110 LCD 7 CE 6 RST 5 DC 4 DIN 3 CLK 2 LIGHT 3.3V VCC GND GND
■ 라이브러리 다운로드
Adafruit GFX 라이브러리 : https://github.com/adafruit/Adafruit-GFX-Library
Adafruit PCD8544 Nokia 5110 LCD library : https://github.com/adafruit/Adafruit-PCD8544-Nokia-5110-LCD-library
위의 두 가지 라이브러리를 다운로드 받아서 압축을 풀고 아두이노 설치폴더 하위의 Libraries 폴더에 복사해 넣으면 된다. 참고로 GFX 라이브러리는 예전 OLED LCD 사용에 대한 글에서도 사용한 라이브러리이다.
Adafruit-GFX-Library-master.zip다운로드 Adafruit-PCD8544-Nokia-5110-LCD-library-master.zip다운로드
■ 소스
아래 소스는 라이브러리 설치 시 Example 로 제공되는 소스(pcdtest.ino)이며 핀 연결 부분을 나의 연결에 맞게 수정했으며 백라이트 제어 부분을 추가한 소스이다.
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357 /*********************************************************************This is an example sketch for our Monochrome Nokia 5110 LCD DisplaysPick one up today in the adafruit shop!------> http://www.adafruit.com/products/338These displays use SPI to communicate, 4 or 5 pins are required tointerfaceAdafruit invests time and resources providing this open source code,please support Adafruit and open-source hardware by purchasingproducts from Adafruit!Written by Limor Fried/Ladyada for Adafruit Industries.BSD license, check license.txt for more informationAll text above, and the splash screen must be included in any redistribution*********************************************************************/#include <SPI.h>#include <Adafruit_GFX.h>#include <Adafruit_PCD8544.h>#define PIN_BL 2 //백라이트 제어를 위한 핀연결// Software SPI (slower updates, more flexible pin options):// pin 7 - Serial clock out (SCLK)// pin 6 - Serial data out (DIN)// pin 5 - Data/Command select (D/C)// pin 4 - LCD chip select (CS)// pin 3 - LCD reset (RST)//Adafruit_PCD8544 display = Adafruit_PCD8544(7, 6, 5, 4, 3); //원래 핀연결Adafruit_PCD8544 display = Adafruit_PCD8544(3, 4, 5, 7, 6); //나의 연결에 맞게 수정한 핀연결// Hardware SPI (faster, but must use certain hardware pins):// SCK is LCD serial clock (SCLK) - this is pin 13 on Arduino Uno// MOSI is LCD DIN - this is pin 11 on an Arduino Uno// pin 5 - Data/Command select (D/C)// pin 4 - LCD chip select (CS)// pin 3 - LCD reset (RST)// Adafruit_PCD8544 display = Adafruit_PCD8544(5, 4, 3);// Note with hardware SPI MISO and SS pins aren't used but will still be read// and written to during SPI transfer. Be careful sharing these pins!#define NUMFLAKES 10#define XPOS 0#define YPOS 1#define DELTAY 2#define LOGO16_GLCD_HEIGHT 16#define LOGO16_GLCD_WIDTH 16static const unsigned char PROGMEM logo16_glcd_bmp[] ={ B00000000, B11000000,B00000001, B11000000,B00000001, B11000000,B00000011, B11100000,B11110011, B11100000,B11111110, B11111000,B01111110, B11111111,B00110011, B10011111,B00011111, B11111100,B00001101, B01110000,B00011011, B10100000,B00111111, B11100000,B00111111, B11110000,B01111100, B11110000,B01110000, B01110000,B00000000, B00110000 };void setup() {//백라이트를 ON 함pinMode(PIN_BL,OUTPUT);digitalWrite(PIN_BL,LOW); //HIGH = Turn Backlight OFF, LOW = Turn Backlight ONSerial.begin(9600);display.begin();// init done// you can change the contrast around to adapt the display// for the best viewing!display.setContrast(50);display.display(); // show splashscreendelay(2000);display.clearDisplay(); // clears the screen and buffer// draw a single pixeldisplay.drawPixel(10, 10, BLACK);display.display();delay(2000);display.clearDisplay();// draw many linestestdrawline();display.display();delay(2000);display.clearDisplay();// draw rectanglestestdrawrect();display.display();delay(2000);display.clearDisplay();// draw multiple rectanglestestfillrect();display.display();delay(2000);display.clearDisplay();// draw mulitple circlestestdrawcircle();display.display();delay(2000);display.clearDisplay();// draw a circle, 10 pixel radiusdisplay.fillCircle(display.width()/2, display.height()/2, 10, BLACK);display.display();delay(2000);display.clearDisplay();testdrawroundrect();delay(2000);display.clearDisplay();testfillroundrect();delay(2000);display.clearDisplay();testdrawtriangle();delay(2000);display.clearDisplay();testfilltriangle();delay(2000);display.clearDisplay();// draw the first ~12 characters in the fonttestdrawchar();display.display();delay(2000);display.clearDisplay();// text display textsdisplay.setTextSize(1);display.setTextColor(BLACK);display.setCursor(0,0);display.println("Hello, world!");display.setTextColor(WHITE, BLACK); // 'inverted' textdisplay.println(3.141592);display.setTextSize(2);display.setTextColor(BLACK);display.print("0x"); display.println(0xDEADBEEF, HEX);display.display();delay(2000);// rotation exampledisplay.clearDisplay();display.setRotation(1); // rotate 90 degrees counter clockwise, can also use values of 2 and 3 to go further.display.setTextSize(1);display.setTextColor(BLACK);display.setCursor(0,0);display.println("Rotation");display.setTextSize(2);display.println("Example!");display.display();delay(2000);// revert back to no rotationdisplay.setRotation(0);// miniature bitmap displaydisplay.clearDisplay();display.drawBitmap(30, 16, logo16_glcd_bmp, 16, 16, 1);display.display();// invert the displaydisplay.invertDisplay(true);delay(1000);display.invertDisplay(false);delay(1000);// draw a bitmap icon and 'animate' movementtestdrawbitmap(logo16_glcd_bmp, LOGO16_GLCD_WIDTH, LOGO16_GLCD_HEIGHT);}void loop() {}void testdrawbitmap(const uint8_t *bitmap, uint8_t w, uint8_t h) {uint8_t icons[NUMFLAKES][3];randomSeed(666); // whatever seed// initializefor (uint8_t f=0; f< NUMFLAKES; f++) {icons[f][XPOS] = random(display.width());icons[f][YPOS] = 0;icons[f][DELTAY] = random(5) + 1;Serial.print("x: ");Serial.print(icons[f][XPOS], DEC);Serial.print(" y: ");Serial.print(icons[f][YPOS], DEC);Serial.print(" dy: ");Serial.println(icons[f][DELTAY], DEC);}while (1) {// draw each iconfor (uint8_t f=0; f< NUMFLAKES; f++) {display.drawBitmap(icons[f][XPOS], icons[f][YPOS], logo16_glcd_bmp, w, h, BLACK);}display.display();delay(200);// then erase it + move itfor (uint8_t f=0; f< NUMFLAKES; f++) {display.drawBitmap(icons[f][XPOS], icons[f][YPOS], logo16_glcd_bmp, w, h, WHITE);// move iticons[f][YPOS] += icons[f][DELTAY];// if its gone, reinitif (icons[f][YPOS] > display.height()) {icons[f][XPOS] = random(display.width());icons[f][YPOS] = 0;icons[f][DELTAY] = random(5) + 1;}}}}void testdrawchar(void) {display.setTextSize(1);display.setTextColor(BLACK);display.setCursor(0,0);for (uint8_t i=0; i < 168; i++) {if (i == '\n') continue;display.write(i);//if ((i > 0) && (i % 14 == 0))//display.println();}display.display();}void testdrawcircle(void) {for (int16_t i=0; i<display.height(); i+=2) {display.drawCircle(display.width()/2, display.height()/2, i, BLACK);display.display();}}void testfillrect(void) {uint8_t color = 1;for (int16_t i=0; i<display.height()/2; i+=3) {// alternate colorsdisplay.fillRect(i, i, display.width()-i*2, display.height()-i*2, color%2);display.display();color++;}}void testdrawtriangle(void) {for (int16_t i=0; i<min(display.width(),display.height())/2; i+=5) {display.drawTriangle(display.width()/2, display.height()/2-i,display.width()/2-i, display.height()/2+i,display.width()/2+i, display.height()/2+i, BLACK);display.display();}}void testfilltriangle(void) {uint8_t color = BLACK;for (int16_t i=min(display.width(),display.height())/2; i>0; i-=5) {display.fillTriangle(display.width()/2, display.height()/2-i,display.width()/2-i, display.height()/2+i,display.width()/2+i, display.height()/2+i, color);if (color == WHITE) color = BLACK;else color = WHITE;display.display();}}void testdrawroundrect(void) {for (int16_t i=0; i<display.height()/2-2; i+=2) {display.drawRoundRect(i, i, display.width()-2*i, display.height()-2*i, display.height()/4, BLACK);display.display();}}void testfillroundrect(void) {uint8_t color = BLACK;for (int16_t i=0; i<display.height()/2-2; i+=2) {display.fillRoundRect(i, i, display.width()-2*i, display.height()-2*i, display.height()/4, color);if (color == WHITE) color = BLACK;else color = WHITE;display.display();}}void testdrawrect(void) {for (int16_t i=0; i<display.height()/2; i+=2) {display.drawRect(i, i, display.width()-2*i, display.height()-2*i, BLACK);display.display();}}void testdrawline() {for (int16_t i=0; i<display.width(); i+=4) {display.drawLine(0, 0, i, display.height()-1, BLACK);display.display();}for (int16_t i=0; i<display.height(); i+=4) {display.drawLine(0, 0, display.width()-1, i, BLACK);display.display();}delay(250);display.clearDisplay();for (int16_t i=0; i<display.width(); i+=4) {display.drawLine(0, display.height()-1, i, 0, BLACK);display.display();}for (int8_t i=display.height()-1; i>=0; i-=4) {display.drawLine(0, display.height()-1, display.width()-1, i, BLACK);display.display();}delay(250);display.clearDisplay();for (int16_t i=display.width()-1; i>=0; i-=4) {display.drawLine(display.width()-1, display.height()-1, i, 0, BLACK);display.display();}for (int16_t i=display.height()-1; i>=0; i-=4) {display.drawLine(display.width()-1, display.height()-1, 0, i, BLACK);display.display();}delay(250);display.clearDisplay();for (int16_t i=0; i<display.height(); i+=4) {display.drawLine(display.width()-1, 0, 0, i, BLACK);display.display();}for (int16_t i=0; i<display.width(); i+=4) {display.drawLine(display.width()-1, 0, i, display.height()-1, BLACK);display.display();}delay(250);}cs
소스는 setup() 에서 여러가지 도형 및 문자를 출력하는 function을 순차적으로 실행하고 있다. 각 function 들을 자세히 보면 어떻게 도형과 문자 그리고 애니메이션을 만드는지 알 수 있을 것이다. 복잡한 부분은 라이브러리와 되어 있어서 자세히 살펴보면 별로 어려운 부분은 없다. 대부분의 기능들이 예를 들어 display.clearDisplay(); 같이 간단하게 제어가 가능하게 되어있다.
■ 추가사항 (2017.04.20) : 위의 소스에서 텍스트 표시하는 부분만 잘라서 정리해 보았다. 아무래도 이 디스플레이를 가지고 그래픽 보다는 텍스트 표시 용도로 사용할 경우가 많을 것으로 보여서 정리해 보았다.
123456789101112131415161718192021222324252627282930313233343536373839 #include <SPI.h>#include <Adafruit_GFX.h>#include <Adafruit_PCD8544.h>#define PIN_BL 2 //백라이트 제어를 위한 핀연결//SCLK, DIN, DC, CE, RST 핀연결Adafruit_PCD8544 display = Adafruit_PCD8544(3, 4, 5, 7, 6);void setup(){//백라이트를 ON 함, HIGH = Turn Backlight OFF, LOW = Turn Backlight ONpinMode(PIN_BL,OUTPUT);digitalWrite(PIN_BL,LOW);//디스플레이 초기화display.begin();//디스플레이 Contrast 조절 (값이 올라가면 진해짐)display.setContrast(60);//텍스트 디스플레이display.clearDisplay(); //디스플레이 지우기display.setTextSize(1); //텍스트 사이즈 조절display.setTextColor(BLACK); //텍스트 색display.setCursor(0,0); //커서 좌표display.println("Hello, world!"); //표시 텍스트display.setTextColor(WHITE, BLACK); // 'inverted' text (배경 까맣게 글자 하얗게)display.println(3.141592); //숫자 표시display.setTextSize(2); //텍스트 사이즈 조절display.setTextColor(BLACK); //텍스트 색display.print("0x"); //표시 텍스트display.println(0xDEADBEEF, HEX); //HEX 쓰기display.display(); //위의 설정내용 표시}void loop(){}cs 주석을 나름대로 상세하게 달아 보았다.
'아두이노' 카테고리의 다른 글
| [아두이노] 아두이노 나노를 이용한 무선조종 보트 만들기 (5) | 2017.10.11 |
|---|---|
| 아두이노를 좋아하는 사람들의 모임 소개 (0) | 2017.07.20 |
| [아두이노] 노키아 5110 LCD (Nokia 5110 LCD) 의 사용 (0) | 2017.04.04 |
| [아두이노] SSR (Solid State Relay) 의 사용 (6) | 2017.01.24 |
| [아두이노] MQ-3 알코올센서 모듈의 이용 (3) | 2017.01.06 |