Дисплей от Motorola C201

forfrends
Offline
Зарегистрирован: 24.02.2015

Всем привет! имеется дисплей от Motorola C201. Разрешение 96*64. Подключается по I2C. Схему подсмотрел здесь: http://vrtp.ru/index.php?showtopic=9846#
Подошла инициализация от Motorola T190(T191). Привожу код, но написан он не для Ардуино IDE, если не ошибаюсь, для CodeVisionAVR, я использую такой же код, только для Ардуино, и он разбит на несколько файлов, по этому привожу код для CodeVisionAVR:

//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 
/* 
Graphic LCD Motorola t191   
With Windows-1215 codepage (Russian) (hardware i2c mode)
*/ 
// ex: 
// 
// ... 
// lph_init(); 
// ... 
// lph_gotoxy(0,0); 
// printf(lph_printchar,"Hello, World!"); 
// ... 
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 


#define res   PIN_C5 
#define Device_SDA PIN_C4 
#define Device_SLC PIN_C3
#use i2c(master, sda=Device_SDA, scl=Device_SLC)
char char_row,charsel,charpos,chardata;       // for lph_7906 lcd 
int16 ddram; 

//#use delay ( clock=4000000 )

BYTE const TABLE5[240]=            
 {0x00,0x00,0x00,0x00,0x00,   // 20 space           
  0x00,0x00,0x5f,0x00,0x00,   // 21 ! 
  0x00,0x07,0x00,0x07,0x00,   // 22 " 
  0x14,0x7f,0x14,0x7f,0x14,   // 23 # 
  0x24,0x2a,0x7f,0x2a,0x12,   // 24 $ 
  0x23,0x13,0x08,0x64,0x62,   // 25 % 
  0x36,0x49,0x55,0x22,0x50,   // 26 & 
  0x00,0x05,0x03,0x00,0x00,   // 27 ' 
  0x00,0x1c,0x22,0x41,0x00,   // 28 ( 
  0x00,0x41,0x22,0x1c,0x00,   // 29 ) 
  0x14,0x08,0x3e,0x08,0x14,   // 2a * 
  0x08,0x08,0x3e,0x08,0x08,   // 2b + 
  0x00,0x50,0x30,0x00,0x00,   // 2c , 
  0x08,0x08,0x08,0x08,0x08,   // 2d - 
  0x00,0x60,0x60,0x00,0x00,   // 2e . 
  0x20,0x10,0x08,0x04,0x02,   // 2f / 
  0x3e,0x51,0x49,0x45,0x3e,   // 30 0 
  0x00,0x42,0x7f,0x40,0x00,   // 31 1 
  0x42,0x61,0x51,0x49,0x46,   // 32 2 
  0x21,0x41,0x45,0x4b,0x31,   // 33 3 
  0x18,0x14,0x12,0x7f,0x10,   // 34 4 
  0x27,0x45,0x45,0x45,0x39,   // 35 5 
  0x3c,0x4a,0x49,0x49,0x30,   // 36 6 
  0x01,0x71,0x09,0x05,0x03,   // 37 7 
  0x36,0x49,0x49,0x49,0x36,   // 38 8 
  0x06,0x49,0x49,0x29,0x1e,   // 39 9 
  0x00,0x36,0x36,0x00,0x00,   // 3a : 
  0x00,0x56,0x36,0x00,0x00,   // 3b ; 
  0x08,0x14,0x22,0x41,0x00,   // 3c < 
  0x14,0x14,0x14,0x14,0x14,   // 3d = 
  0x00,0x41,0x22,0x14,0x08,   // 3e > 
  0x02,0x01,0x51,0x09,0x06,   // 3f ? 
  0x32,0x49,0x79,0x41,0x3e,   // 40 @ 
  0x7e,0x11,0x11,0x11,0x7e,   // 41 A 
  0x7f,0x49,0x49,0x49,0x36,   // 42 B 
  0x3e,0x41,0x41,0x41,0x22,   // 43 C 
  0x7f,0x41,0x41,0x22,0x1c,   // 44 D 
  0x7f,0x49,0x49,0x49,0x41,   // 45 E 
  0x7f,0x09,0x09,0x09,0x01,   // 46 F 
  0x3e,0x41,0x49,0x49,0x7a,   // 47 G 
  0x7f,0x08,0x08,0x08,0x7f,   // 48 H 
  0x00,0x41,0x7f,0x41,0x00,   // 49 I 
  0x20,0x40,0x41,0x3f,0x01,   // 4a J 
  0x7f,0x08,0x14,0x22,0x41,   // 4b K 
  0x7f,0x40,0x40,0x40,0x40,   // 4c L 
  0x7f,0x02,0x0c,0x02,0x7f,   // 4d M 
  0x7f,0x04,0x08,0x10,0x7f,   // 4e N 
  0x3e,0x41,0x41,0x41,0x3e    // 4f O 
};    


BYTE const TABLE6[240]=            {0x7f,0x09,0x09,0x09,0x06,   // 50 P 
  0x3e,0x41,0x51,0x21,0x5e,   // 51 Q 
  0x7f,0x09,0x19,0x29,0x46,   // 52 R 
  0x46,0x49,0x49,0x49,0x31,   // 53 S 
  0x01,0x01,0x7f,0x01,0x01,   // 54 T 
  0x3f,0x40,0x40,0x40,0x3f,   // 55 U 
  0x1f,0x20,0x40,0x20,0x1f,   // 56 V 
  0x3f,0x40,0x38,0x40,0x3f,   // 57 W 
  0x63,0x14,0x08,0x14,0x63,   // 58 X 
  0x07,0x08,0x70,0x08,0x07,   // 59 Y 
  0x61,0x51,0x49,0x45,0x43,   // 5a Z 
  0x00,0x7f,0x41,0x41,0x00,   // 5b [ 
  0x02,0x04,0x08,0x10,0x20,   // 5c 
  0x00,0x41,0x41,0x7f,0x00,   // 5d 
  0x04,0x02,0x01,0x02,0x04,   // 5e 
  0x40,0x40,0x40,0x40,0x40,   // 5f 
  0x00,0x01,0x02,0x04,0x00,   // 60 
  0x20,0x54,0x54,0x54,0x78,   // 61 a 
  0x7f,0x48,0x44,0x44,0x38,   // 62 b 
  0x38,0x44,0x44,0x44,0x20,   // 63 c 
  0x38,0x44,0x44,0x48,0x7f,   // 64 d 
  0x38,0x54,0x54,0x54,0x18,   // 65 e 
  0x08,0x7e,0x09,0x01,0x02,   // 66 f 
  0x0c,0x52,0x52,0x52,0x3e,   // 67 g 
  0x7f,0x08,0x04,0x04,0x78,   // 68 h 
  0x00,0x44,0x7d,0x40,0x00,   // 69 i 
  0x20,0x40,0x44,0x3d,0x00,   // 6a j 
  0x7f,0x10,0x28,0x44,0x00,   // 6b k 
  0x00,0x41,0x7f,0x40,0x00,   // 6c l 
  0x7c,0x04,0x18,0x04,0x78,   // 6d m 
  0x7c,0x08,0x04,0x04,0x78,   // 6e n 
  0x38,0x44,0x44,0x44,0x38,   // 6f o 
  0x7c,0x14,0x14,0x14,0x08,   // 70 p 
  0x08,0x14,0x14,0x18,0x7c,   // 71 q 
  0x7c,0x08,0x04,0x04,0x08,   // 72 r 
  0x48,0x54,0x54,0x54,0x20,   // 73 s 
  0x04,0x3f,0x44,0x40,0x20,   // 74 t 
  0x3c,0x40,0x40,0x20,0x7c,   // 75 u 
  0x1c,0x20,0x40,0x20,0x1c,   // 76 v 
  0x3c,0x40,0x30,0x40,0x3c,   // 77 w 
  0x44,0x28,0x10,0x28,0x44,   // 78 x 
  0x0c,0x50,0x50,0x50,0x3c,   // 79 y 
  0x44,0x64,0x54,0x4c,0x44,   // 7a z 
  0x00,0x08,0x36,0x41,0x00,   // 7b 
  0x00,0x00,0x7f,0x00,0x00,   // 7c 
  0x00,0x41,0x36,0x08,0x00,   // 7d 
  0x10,0x08,0x08,0x10,0x08,   // 7e 
  0x78,0x46,0x41,0x46,0x78    // 7f 
};  

BYTE const TABLE7[240]=            
 {
 0x7E, 0x11, 0x11, 0x11, 0x7E,//c0 A  0x80
 0x7F, 0x49, 0x49, 0x49, 0x30,//c1 Б 
 0x7F, 0x49, 0x49, 0x49, 0x36,//c2 B
 0x7F, 0x01, 0x01, 0x01, 0x01,//c3 Г
 0x60, 0x3E, 0x21, 0x3F, 0x60,//c4 Д
 0x7F, 0x49, 0x49, 0x49, 0x41,//c5 Е
 0x67, 0x18, 0x7F, 0x18, 0x67,//c6 Ж
 0x22, 0x41, 0x49, 0x49, 0x36,//c7 З
 0x7F, 0x10, 0x08, 0x04, 0x7F,//c8 И
 0x7F, 0x10, 0x09, 0x04, 0x7F,//c9 Й
 0x7F, 0x08, 0x14, 0x22, 0x41,//ca К
 0x40, 0x3E, 0x01, 0x01, 0x7E,//cb Л
 0x7F, 0x02, 0x04, 0x02, 0x7F,//cc М
 0x7F, 0x08, 0x08, 0x08, 0x7F,//cd Н
 0x3E, 0x41, 0x41, 0x41, 0x3E,//ce О
 0x7F, 0x01, 0x01, 0x01, 0x7F,//cf П
 0x7F, 0x09, 0x09, 0x09, 0x06,//d0 Р
 0x3E, 0x41, 0x41, 0x41, 0x22,//d1 С
 0x01, 0x01, 0x7F, 0x01, 0x01,//d2 Т
 0x27, 0x48, 0x48, 0x48, 0x3F,//d3 У
 0x1E, 0x21, 0x7F, 0x21, 0x1E,//d4 Ф
 0x63, 0x14, 0x08, 0x14, 0x63,//d5 Х
 0x3F, 0x20, 0x20, 0x3F, 0x40,//d6 Ц
 0x1F, 0x10, 0x10, 0x10, 0x7F,//d7 Ч
 0x7F, 0x40, 0x7F, 0x40, 0x7F,//d8 Ш
 0x3F, 0x20, 0x3F, 0x20, 0x7F,//d9 Щ
 0x01, 0x7F, 0x44, 0x44, 0x38,//da Ъ
 0x7F, 0x44, 0x7C, 0x00, 0x7F,//db Ы
 0x7F, 0x44, 0x44, 0x44, 0x38,//dc Ь
 0x22, 0x41, 0x49, 0x49, 0x3E,//dd Э
 0x7F, 0x08, 0x7F, 0x41, 0x7F,//de Ю
 0x46, 0x29, 0x19, 0x09, 0x7F,//df Я
 0x20, 0x54, 0x54, 0x54, 0x78,//e0 а
 0x3C, 0x4A, 0x4A, 0x4B, 0x30,//e1 б
 0x7C, 0x54, 0x54, 0x58, 0x20,//e2 в
 0x7C, 0x04, 0x04, 0x04, 0x04,//e3 г
 0x60, 0x38, 0x24, 0x3C, 0x60,//e4 д
 0x38, 0x54, 0x54, 0x54, 0x18,//e5 е
 0x74, 0x08, 0x7C, 0x08, 0x74,//e6 ж
 0x28, 0x44, 0x54, 0x54, 0x28,//e7 з
 0x7C, 0x20, 0x10, 0x08, 0x7C,//e8 и
 0x7C, 0x21, 0x12, 0x09, 0x7C,//e9 й
 0x7C, 0x10, 0x10, 0x28, 0x44,//ea к
 0x40, 0x78, 0x04, 0x04, 0x7C,//eb л
 0x7C, 0x08, 0x10, 0x08, 0x7C,//ec м
 0x7C, 0x10, 0x10, 0x10, 0x7C,//ed н
 0x38, 0x44, 0x44, 0x44, 0x38,//ee о
 0x7C, 0x04, 0x04, 0x04, 0x7C//ef п
};  
BYTE const TABLE8[80]=            
 {
 0x7C, 0x14, 0x14, 0x14, 0x08,//f0 р
 0x38, 0x44, 0x44, 0x44, 0x28,//f1 с
 0x04, 0x04, 0x7C, 0x04, 0x04,//f2 т
 0x0C, 0x50, 0x50, 0x50, 0x3C,//f3 у
 0x18, 0x24, 0x7C, 0x24, 0x18,//f4 ф
 0x44, 0x28, 0x10, 0x28, 0x44,//f5 х
 0x3C, 0x20, 0x20, 0x3C, 0x40,//f6 ц
 0x1C, 0x20, 0x20, 0x20, 0x7C,//f7 ч
 0x7C, 0x40, 0x7C, 0x40, 0x7C,//f8 ш
 0x3C, 0x20, 0x3C, 0x20, 0x7C,//f9 щ
 0x04, 0x7C, 0x48, 0x48, 0x30,//fa ъ
 0x7C, 0x48, 0x48, 0x30, 0x7C,//fb ы
 0x7C, 0x48, 0x48, 0x48, 0x30,//fc ь
 0x28, 0x44, 0x54, 0x54, 0x38,//fd э
 0x7C, 0x38, 0x44, 0x44, 0x38,//fe ю
 0x48, 0x34, 0x14, 0x14, 0x7C,//ff я

};  


void    lph_init(void); 
void    video_mode(unsigned char mode);
void    lph_write_data(char byteforlph_data); 
void    lph_gotoxy(int8 xlph, int8 ylph); 
void    lph_erase_y(int8 ylph); 
void    lph_erase_x(int8 xlph); 
void    lph_printchar(int8 cvar); 
void    table_to_lphlcd(void); 
void    lph_clear_screen(void); 
void    lph_clear_xy(int8 xlph, int8 ylph); 
void    lph_print_uparrow(void); 
void    lph_print_downarrow(void); 
void    lph_print_leftarrow(void); 
void    lph_print_rightarrow(void); 
void    lph_print_degree(void); 
void    lph_print_lowbatdegree(void); 


  void video_mode(unsigned char mode)
   {
                                //1 -invert //0 -normal
   i2c_start();                              
   if(mode > 0)                
   {
    //78;00;20;0c
   i2c_write(0x78);i2c_write(0x00);i2c_write(0x20);i2c_write(0x0C);
   }
   else
   {
    //78;00;20;0c
   i2c_write(0x78);i2c_write(0x00);i2c_write(0x20);i2c_write(0x0D);
  }
   i2c_stop();
  }
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 
void lph_init(void) 
{ 
  output_low(res);
  delay_ms(500);
  output_high(res);
  output_float(PIN_C3);
  output_float(PIN_C4); 
  i2c_start();
  i2c_write(0x78);
  i2c_write(0x00);
  i2c_write(0x31);
  i2c_write(0x14);
  i2c_write(0x06);
  i2c_write(0x30);
  i2c_write(0x11);
  i2c_write(0x05);
  i2c_write(0x31);
  i2c_write(0x80); //контраст
  i2c_write(0x0C);
  i2c_write(0x30);
  i2c_write(0x0C);
  i2c_write(0x40);
  i2c_write(0x80);
  i2c_stop();
  lph_clear_screen();
} 

///////////////////////////////////////////////////////////////////////////////// 
void lph_write_data(char byteforlph_data) 
{ 
  i2c_start();
  i2c_write(0x78);
  i2c_write(0x40);
  i2c_write(byteforlph_data);
  i2c_stop();
}
////////////////////////////////////////////////////////////////////////////////// 
void lph_gotoxy(int8 xlph, int8 ylph)      // Siemens LCD A50 Position cursor 
{ 
   i2c_start();
   i2c_write(0x78);i2c_write(0x00);i2c_write(0x30);i2c_write(0x40|(ylph&0x07));i2c_write(0x80|(xlph&0x7f));
   i2c_stop();
} 
////////////////////////////////////////////////////////////////////////////////// 
void lph_erase_y(int8 ylph) 
{ 
     int i; 
  lph_gotoxy(0,ylph); 
  i2c_start();
  i2c_write(0x78);
  i2c_write(0x40);
  for(i = 0; i < 98; i++)
  {
   i2c_write(0x00); 
  }  
  i2c_stop();
}
////////////////////////////////////////////////////////////////////////////////// 
void lph_erase_x(int8 xlph) 
{ 
 
 char column; 

  for (column=0;column!=8;column++){ 
    lph_gotoxy(xlph,column); 
    lph_write_data(0x00); 
    lph_write_data(0x00); 
    lph_write_data(0x00); 
    lph_write_data(0x00); 
    lph_write_data(0x00); 
    lph_write_data(0x00); 

  } 
} 
////////////////////////////////////////////////////////////////////////////////// 

void lph_printchar(int8 cvar)               // Write 1 character to LCD 
{ 
  charsel=cvar; 
  table_to_lphlcd(); 
} 
////////////////////////////////////////////////////////////////////////////////// 
void table_to_lphlcd(void)   // extract ascii from tables & write to LCD 
{ 
  if (charsel<0x20)return;
  if ((charsel<0xc0)&(charsel>0x7f))return; 

  for (char_row=0;char_row<5;char_row++) {      // 5 bytes 

    if (charsel<0x50){charpos=(((charsel&0xff)-0x20)*5);chardata=TABLE5[(charpos+char_row)];}            // use TABLE5 
    else if (charsel<0x80){charpos=(((charsel&0xff)-0x50)*5);chardata=TABLE6[(charpos+char_row)];}            // use TABLE6 
    else if (charsel<0xf0){charpos=(((charsel&0xff)-0xc0)*5);chardata=TABLE7[(charpos+char_row)];}            // use TABLE6 
    else /*if (charsel<=0xff)*/{charpos=(((charsel&0xff)-0xf0)*5);chardata=TABLE8[(charpos+char_row)];}            // use TABLE6 


    lph_write_data(chardata);      // send data to lph 
  } 

  lph_write_data(0x00);      //    1 byte (always blank) 

} 
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 


void lph_clear_screen(void) 
{ 
  lph_erase_y(0); 
  lph_erase_y(1); 
  lph_erase_y(2); 
  lph_erase_y(3); 
  lph_erase_y(4); 
  lph_erase_y(5); 
  lph_erase_y(6); 
  lph_erase_y(7); 
} 

//////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 


void lph_clear_xy(int8 xlph, int8 ylph) 
{ 

  lph_gotoxy(xlph,ylph); 
  lph_printchar(" "); 


} 
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 
void lph_print_uparrow(void) 
{ 
  lph_write_data(0x04); 
  lph_write_data(0x02); 
  lph_write_data(0x7f); 
  lph_write_data(0x02); 
  lph_write_data(0x04); 
  lph_write_data(0x00); 
} 
// 
void lph_print_downarrow(void) 
{ 
  lph_write_data(0x10); 
  lph_write_data(0x20); 
  lph_write_data(0x7f); 
  lph_write_data(0x20); 
  lph_write_data(0x10); 
  lph_write_data(0x00); 
} 
// 
void lph_print_leftarrow(void) 
{ 
  lph_write_data(0x08); 
  lph_write_data(0x1c); 
  lph_write_data(0x2a); 
  lph_write_data(0x08); 
  lph_write_data(0x08); 
  lph_write_data(0xf8); 
} 
// 
void lph_print_rightarrow(void) 
{ 
  lph_write_data(0x08); 
  lph_write_data(0x08); 
  lph_write_data(0x2a); 
  lph_write_data(0x1c); 
  lph_write_data(0x08); 
  lph_write_data(0x00); 
} 
// 
void lph_print_degree(void) 
{ 
  lph_write_data(0x00); 
  lph_write_data(0x06); 
  lph_write_data(0x09); 
  lph_write_data(0x09); 
  lph_write_data(0x06); 
  lph_write_data(0x00); 


} 
// 
void lph_print_lowbatdegree(void) 
{ 
  lph_write_data(0x00); 
  lph_write_data(0x06); 
  lph_write_data(0x0f); 
  lph_write_data(0x0f); 
  lph_write_data(0x06); 
  lph_write_data(0x00); 

} 
//////////////////////////////////////////////////////////////////////////////////////////////////////////

В общем дисплей работает, все отображает. Но есть один огромный минус: он показывает верхногами. То есть начало координат находится не слева вверху, а справа внизу. Текст выводится справа на лево и снизу вверх...
Надо как-то перевернуть дисплей. Но что-то не могу найти регистр, который за это отвечает. Может кто-то может подсказать? Физически перевернуть дисплей нельзя, просто не станет на свое место. Вот команды инициализации:

0x00
0x31
0x14
0x06
0x30
0x11
0x05
0x31
0x9A - contrast 0x9A*/,
0x0C
0x30
0x0C - D - inverse, C - normal,
0x40
0x80
 
Я попробовал изменять биты в командах 0x0C, 0x30 и 0x0C (D - inverse, C - normal), единственное что удалось добиться - отражение букв по горизонтали или вертикали, именно каждого символа по отдельности, а не строк целиком.
alex_kotl
Offline
Зарегистрирован: 21.03.2018

Если контроллер ST7558, ковыряй регистр Ext. display control MX, MY (см.даташит, попробуй добавить в инициализацию 0x2E)

forfrends
Offline
Зарегистрирован: 24.02.2015

Очень похоже. Но инициализация от ST7558 не подходит. Вот пример инициализации:

{
0x2E,           // MXMY
0x21,           // Extend Set H=1
0x12,           // Bias
0xC0,           // VOP
0x0B,           // Boost
0x20,           // Normal Set H=0
0x11,           // PRS
0x00,           // nop
0x40,           // Y addr
 0x80,           // X addr
},
cmd_invert[]= {CONTROL_RS_CMD, 0x20, 0x0D},
cmd_on[]= {CONTROL_RS_CMD, 0x20, 0x0C},
cmd_off[]= {CONTROL_RS_CMD, 0x20, 0x08};
 
А вот инициализация, которая подходит к моему дисплею:
 
{
0x00,
0x31,
0x14,
0x06,
0x30,
0x11,
0x05,
0x31,
0x9A /*contrast 0x9A*/,
0x0C,
0x30,
0x0C /*D - inverse, C - normal*/,
0x40,
0x80
};
byte gotoxylcd [5] = {0x00, 0x30, 0x40, 0x80};
byte contrast [3] = {0x00, 0x31, 0x9A};
byte erase_ylcd[9] = {0x40, 0x00 };

Есть несколько одинаковых моментов, но в остальном инициализации разные. Только что попробовал инициализацию из даташита на ST7558, страница 48. Но дисплей молчит. Скорее всего используется другой контроллер.

alex_kotl
Offline
Зарегистрирован: 21.03.2018

Есть инфа, что возможно контроллер PCF8548, посмотри даташит