4a4ik
31 июля 2014 г.
nokia 5110 LCD дисплей AVR
Теперь я расскажу как работать с дисплеем от Нокии 5110.
Матрица состоит из 48 × 84 пикселей. 48 строчек, 84 столбца.
Но питать микросхему отвечающую за работу дисплея нужно от 2.7 В до 3.3 В.
Подсветка также питается от 3.3 В или можно от 5 В через резистор 1К.
Также советуют ставить резисторы 10К на все остальные выводы, если МК питается от 5 В.
Можно работать и с 5 В, но могут быть проблемы с отображением и дисплей быстрее придёт в негодность.
Я заказывал с Ебея и в моём случае для того чтобы включить подсветку нужно было заземлить вывод LED.
Есть несколько вариантов расположения выводов:
Номер вывода | Обозначение | Функция | Примечание |
---|---|---|---|
1 | VCC | Питание | |
2 | GND | Земля | |
3 | SCE (CE) | Выбор чипа | можно просто заземлить |
4 | RST | RESET | активно при лог 0 |
5 | D/C (DC) | выбор режима | команды лог 0 дата лог 1 |
6 | DN (DIN) | Дата | передаётся байт данных |
7 | SCLK (CLK) | Serial clock, линия синхронизации | |
8 | LED (LIGHT) | Подсветка | 3.3V |
На самом деле это считывается когда мы передаём последний бит данных, но нет разницы когда мы выберем работаем ли мы с данными или командами, главное чтобы при передаче последнего (0) бита стояло нужное нам значение.
Передача данных происходит следующим образом: Мы передаём байт данных по выводу DN, начиная с последнего 7 бита. Нужно выставить этот бит и установить на SCLK лог 1, в этот момент начинает передаваться информация к контроллеру, затем нужно сбросить SCLK, выставить 6 бит на DN, снова выставить 1 на SCLK и продолжать так до тех пор пока не передадим целый байт.
Источник
SamPawno
Ремонт шлейфа дисплея Nokia 5110 84×48
#1 Дим » 17 июня 2019, 22:00
Adafruit_PCD8544 display = Adafruit_PCD8544 ( 3 , 4 , 5 , 6 , 7 );
#define NUMFLAKES 10
#define XPOS 0
#define YPOS 1
#define DELTAY 2
#define LOGO16_GLCD_HEIGHT 16
#define LOGO16_GLCD_WIDTH 16
static const unsigned char PROGMEM logo16_glcd_bmp [] =
< B00000001 , B00000000 ,
B00000101 , B01000000 ,
B00000011 , B10000000 ,
B00100001 , B00001000 ,
B11000001 , B00000110 ,
B00110001 , B00011000 ,
B01001101 , B01100100 ,
B00000011 , B10000000 ,
B00000011 , B10000000 ,
B01001101 , B01100100 ,
B00110001 , B00011000 ,
B11000001 , B00000110 ,
B00100001 , B00001000 ,
B00000011 , B10000000 ,
B00000101 , B01000000 ,
B00000001 , B00000000 >;
void setup () <
Serial . begin ( 9600 );
display . begin ();
display . cp437 ( true );
// инициализация выполнена
// вы можете изменить контраст вокруг, чтобы адаптировать дисплей
// для лучшего просмотра!
display . setContrast ( 50 );
display . display (); // показать заставку
delay ( 2000 );
display . clearDisplay (); // очищает экран и буфер
//goto metka; // russian font
// нарисовать один пиксель
display . drawPixel ( 10 , 10 , BLACK );
display . display ();
delay ( 2000 );
display . clearDisplay ();
//рисовать много линий
testdrawline ();
display . display ();
delay ( 2000 );
display . clearDisplay ();
// рисовать прямоугольники
testdrawrect ();
display . display ();
delay ( 2000 );
display . clearDisplay ();
//нарисовать несколько прямоугольников
testfillrect ();
display . display ();
delay ( 2000 );
display . clearDisplay ();
// нарисовать несколько кругов
testdrawcircle ();
display . display ();
delay ( 2000 );
display . clearDisplay ();
// нарисовать круг, радиус 10 пикселей
display . 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 ();
12 символов в шрифте
testdrawchar ();
display . display ();
delay ( 2000 );
display . clearDisplay ();
// тесты отображения текста
display . setTextSize ( 1 );
display . setTextColor ( BLACK );
display . setCursor ( 0 , 0 );
display . println ( «Hello, world!» );
display . setTextColor ( WHITE , BLACK ); //«перевернутый» текст
display . println ( 3.141592 );
display . setTextSize ( 2 );
display . setTextColor ( BLACK );
display .print( «0x» ); display . println ( 0xDEADBEEF , HEX );
display . display ();
delay ( 2000 );
//пример вращения
display . clearDisplay ();
display . setRotation ( 1 ); // повернуть на 90 градусов против часовой стрелки, также можно использовать значения 2 и 3, чтобы идти дальше.
display . setTextSize ( 1 );
display . setTextColor ( BLACK );
display . setCursor ( 0 , 0 );
display . println ( «Rotation» );
display . setTextSize ( 2 );
display . println ( «Example!» );
display . display ();
delay ( 2000 );
// вернуться обратно без вращения
display . setRotation ( 0 );
//metka:
// russian font
display . clearDisplay ();
display . setTextColor ( BLACK );
display . setCursor ( 0 , 0 );
display . setTextSize ( 1 );
display . println ( utf8rus ( «Шрифт 1» ));
display . setTextSize ( 2 );
display . println ( utf8rus ( «Шрифт2» ));
display . setTextSize ( 3 );
display . println ( utf8rus ( «Шр3» ));
display . display ();
delay ( 5000 );
// миниатюрный растровый дисплей
display . clearDisplay ();
display . drawBitmap ( 30 , 16 , logo16_glcd_bmp , 16 , 16 , 1 );
display . display ();
// invert the display
display . invertDisplay ( true );
delay ( 1000 );
display . invertDisplay ( false );
delay ( 1000 );
// нарисовать растровую иконку и анимировать движение
testdrawbitmap ( logo16_glcd_bmp , LOGO16_GLCD_WIDTH , LOGO16_GLCD_HEIGHT );
>
void testdrawbitmap ( const uint8_t * bitmap , uint8_t w , uint8_t h ) <
uint8_t icons [ NUMFLAKES ][ 3 ];
randomSeed ( 666 ); // какое бы семя
// инициализировать
for ( 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 ) <
// нарисовать каждый значок
for ( 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 );
// затем стереть + переместить
for ( uint8_t f = 0 ; f NUMFLAKES ; f ++) <
display . drawBitmap ( icons [ f ][ XPOS ], icons [ f ][ YPOS ], logo16_glcd_bmp , w , h , WHITE );
//подвинь это
icons [ f ][ YPOS ] += icons [ f ][ DELTAY ];
//если его нет, реините
if ( 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 colors
display . 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 );
>
/* Перекодировать русские шрифты из UTF-8 в Windows-1251 */
String utf8rus ( String source )
<
int i , k ;
String target ;
unsigned char n ;
char m [ 2 ] = < '0' , '\0' >;
k = source . length (); i = 0 ;
while ( i k ) <
n = source [ i ]; i ++;
if ( n >= 0xC0 ) <
switch ( n ) <
case 0xD0 : <
n = source [ i ]; i ++;
if ( n == 0x81 ) < n = 0xA8 ; break ; >
if ( n >= 0x90 && n 0xBF ) n = n + 0x30 ;
break ;
>
case 0xD1 : <
n = source [ i ]; i ++;
if ( n == 0x91 ) < n = 0xB8 ; break ; >
if ( n >= 0x80 && n 0x8F ) n = n + 0x70 ;
break ;
>
>
>
m [ 0 ] = n ; target = target + String ( m );
>
return target ;
>
Источник
Дисплей Nokia 5110 – подключение к микроконтроллеру
LCD Nokia 5110 представляет собой монохромный графический дисплей с разрешением 48×84 пикселей, который можно использовать для отображения различной информации в устройствах на микроконтроллерах. В прошлом, радиолюбители для своих поделок доставали подобные дисплеи из телефонов Nokia 3310, в настоящее время можно приобрести готовый модуль под Arduino, где дисплей смонтирован на печатной плате. Дополнительно на плате установлены светодиоды подсветки, синего цвета свечения.
Заказать дисплей можно здесь . В дисплее установлен контроллер PCD8544, напряжение питания может находиться в пределах 2,7…3,3 В, ток потребления составляет 240…320 мкА. Модуль имеет следующие выводы для подключения:
- RST – вывод сброса контроллера дисплея
- CE – вывод разрешения передачи данных
- DC – выбор режима передачи, команда или данные
- DIN – вход передачи данных интерфейса SPI
- CLK – вывод тактирования интерфейса SPI
- VCC – вывод питания дисплея
- LIGHT – вывод управление подсветкой, для включения необходимо подать низкий логический уровень
- GND – общий провод (отрицательный полюс источника питания)
Передача данных осуществляется с помощью стандартного интерфейса SPI, частота тактирования до 4 МГц. Во время сеанса передачи данных, на линии CE необходимо установить низкий логический уровень, тем самым разрешая передачу. Когда на дисплей передается команда, линию DC необходимо “притянуть” к общему проводу (лог. 0), при высоком логическом уровне на линии DC, можно передавать данные, которые непосредственно будут отображаться на дисплее.
При включении дисплея, необходимо обязательно выполнить процедуру сброса, в течение 30 мс после подачи питания, выдать на линию RST отрицательный импульс, минимальная длительность импульса (низкого логического уровня) составляет 100 нс. Лог. 0 на линии RST может присутствовать до подачи питания.
В следующей таблице приведены команды управления дисплеем:
Команда | D/C | Байт команды | Описание | |||||||
DB7 | DB6 | DB5 | DB4 | DB3 | DB2 | DB1 | DB0 | |||
Значение бита H не имеет значения (0 или 1) | ||||||||||
NOP | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | пустая команда |
Function set | 0 | 0 | 0 | 1 | 0 | 0 | PD | V | H | Настройка функций |
Write data | 1 | D7 | D6 | D5 | D4 | D3 | D2 | D1 | D0 | Запись данных |
Бит H=0, базовые команды | ||||||||||
Reserved | 0 | 0 | 0 | 0 | 0 | 0 | 1 | X | X | Зарезервировано |
Display control | 0 | 0 | 0 | 0 | 0 | 1 | D | 0 | E | Настройки отображения |
Reserved | 0 | 0 | 0 | 0 | 1 | X | X | X | X | Зарезервировано |
Y address | 0 | 0 | 1 | 0 | 0 | 0 | Y2 | Y1 | Y0 | Установка адресного указателя для вывода данных (0 ≤ Y ≤ 5) |
X address | 0 | 1 | X6 | X5 | X4 | X3 | X2 | X1 | X0 | Установка адресного указателя для вывода данных (0 ≤ X ≤ 83) |
Бит H=1, расширенные команды | ||||||||||
Reserved | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 1 | Зарезервировано |
0 | 0 | 0 | 0 | 0 | 0 | 0 | 1 | X | ||
Temperature control | 0 | 0 | 0 | 0 | 0 | 0 | 1 | TC1 | TC0 | Установка значения температурного коэффициента |
Reserved | 0 | 0 | 0 | 0 | 0 | 1 | X | X | X | Зарезервировано |
Bias system | 0 | 0 | 0 | 0 | 1 | 0 | BS2 | BS1 | BS0 | Настройка смещения напряжений |
Reserved | 0 | 0 | 1 | X | X | X | X | X | X | Зарезервировано |
Set Vop | 0 | 1 | Vop6 | Vop5 | Vop4 | Vop3 | Vop2 | Vop1 | Vop0 | Установка значения напряжения питания матрицы (контрастность) |
Назначение битов в командах описано в следующей таблице:
Бит | Значение | Описание |
PD | 0 | Контроллер дисплея включен |
1 | Контроллер дисплея выключен | |
V | 0 | Горизонтальная адресация |
1 | Вертикальная адресация | |
H | 0 | Использовать базовый набор команд |
1 | Использовать расширенный набор команд | |
D и E | 00 | Все сегменты дисплея выключены |
01 | Все сегменты дисплея включены | |
10 | Нормальный режим | |
11 | Инверсное отображение | |
TC1 и TC0 | 00 | Температурный коэффициент 0 |
01 | Температурный коэффициент 1 | |
10 | Температурный коэффициент 2 | |
11 | Температурный коэффициент 3 | |
BS2, BS1, BS0 | 000 | 1:100 |
001 | 1:80 | |
010 | 1:65 | |
011 | 1:48 | |
100 | 1:40/1:34 | |
101 | 1:24 | |
110 | 1:18/1:16 | |
111 | 1:10/1:9/1:8 |
Матрица дисплея условно поделена на столбцы, представляющие собой 8 пикселей, то есть когда мы отправляем 1 байт данных на дисплей, он отображается в этом столбце. По ширине (горизонтали) дисплея расположены 84 столбца, по высоте (вертикали) расположены 6 столбцов (то есть всего 6 строк). Адрес необходимого столбца (адресный указатель) задается командами X address, Y address. Ниже на картинке представлена структура матрицы:
Адресный указатель автоматически инкрементируется после каждого отправленного на дисплей байта данных. С помощью бита V команды Function set, можно выбрать порядок заполнения столбцов матрицы, если бит равен 0 (горизонтальная адресация), столбцы матрицы заполняются слева-направо, сверху-вниз, при вертикальной адресации V=1, сверху-вниз, слева-направо. После заполнения последнего столбца (X=83, Y=5), адресный указатель возвращается в левый верхний угол (X=0, Y=0). На следующей картинке изображена схема адресаций:
После процедуры сброса, контроллер дисплея находится в выключенном состоянии, все сегменты погашены, соответственно необходимо выполнить инициализацию, отправив на дисплей следующие байты:
- 0x21 (00100001) – команда настройки функций: включить контроллер дисплея, горизонтальная адресация, выбрать расширенный набор команд.
- 0x13 (00010011) – команда установки смещения напряжений (Bias system), в указанной команде выбрано значение 1:48. Значение смещения влияет на внутренний генератор напряжения, питающий матрицу дисплея. Внутренний генератор способен повышать напряжение до 8,5 В, которое влияет на контрастность изображения.
- 0x04 (00000100) – команда установки температурного коэффициента, здесь выбран 0-й коэффициент. Данный коэффициент устанавливает кривую зависимости напряжение питания матрицы (контрастность) от температуры окружающей среды. При понижении температуры контрастность автоматически увеличивается, всего можно выбрать 4 различных коэффициента, соответствующие кривые можно посмотреть в даташите.
- 0xC1 (11000001) – команда установки контрастности дисплея, в данном случае величина контрастности равна 0x65 (1000001). Значение может варьироваться от 0x00 до 0x7F. От этого значения зависит напряжение питания матрицы.
- 0x20 (00100000) – команда настройки функций: включить контроллер дисплея, горизонтальная адресация, выбрать стандартный набор команд. Здесь мы возвращаемся на стандартный набор команд.
- 0x0С (00001100) – команда настройки отображения: выбрать нормальный режим работы.
После инициализации дисплей готов к работе, но необходимо выполнить еще одно действие, после сброса и инициализации состояние сегментов не определено, и дисплей будет показывать мусор, поэтому следует выполнить очистку, записав во все столбцы значение 0x00.
На следующей картинке показана схема подключения дисплея Nokia 5110 к микроконтроллеру PIC16F628A:
Основная часть кода программы приведена ниже (полный код доступен для скачивания в конце статьи):
Источник