LCD控制器TM1621/HT1621要点1)由公共输出口COM0-COM3和段输出口SEG0-SEG23控制LCD的段码;
2)3个关键数据口:
a)CS:片选,低电平有效;
b)WR:读写控制,上升沿从MCU读取数据;
c)DATA:数据,命令是大端位序,数据是小端位序;
3)命令结构:3bit标识(LCD_FLAG_CMD)+9bit命令
4)写数据到RAM:3bit标识(LCD_FLAG_DATA)+6bit地址+若干bit数据(数据是小端)
定义
#define LCD_BIAS_1P2 (0<<1) //1/2偏压#define LCD_BIAS_1P3 (1<<1) //1/3偏压 #define LCD_USE_COM2 (0<<3) //使用2个公共口 #define LCD_USE_COM3 (1<<3) //使用3个公共口 #define LCD_USE_COM4 (2<<3) //使用4个公共口 #define LCD_CMD_BIAS_COM (0x40) //设置公共口和偏压的命令 #define LCD_CMD_ON (0x6) //打开 #define LCD_CMD_OFF (0x4) //关闭 #define LCD_CMD_Normal (0x1C6) //普通模式 #define LCD_CMD_SYS_EN (2) //打开系统振荡器和LCD偏压发生器 #define LCD_CMD_SYS_DIS (0) //关闭系统振荡器和LCD偏压发生器 #define LCD_RC256 (0x30) //系统时钟源片内RC 256K振荡器 #define LCD_XTAL 0x28 //0b1000 0010 1000 外部接时钟 #define LCD_WDTDIS1 0X0A //0b1000 0000 1010 禁止看门狗 #define LCD_FLAG_CMD (4) //命令标识100 #define LCD_FLAG_DATA (5) //数据标识101
复制代码/** * 发送大端数据 */ static void lcd_sendBeData(LcdStr* ps,u32 n, int nBit) { for (int i = nBit; --i >= 0;) { LCD_WR_L(); LCD_WriteBit((n >> i) & 1); LCD_DELAY(); LCD_WR_H(); LCD_DELAY(); } } /** * 发送小端数据 */ static void lcd_sendLeData(LcdStr* ps,u32 n, int nBit) { for (int i = 0; i < nBit; i++) { LCD_WR_L(); LCD_WriteBit((n >> i) & 1); LCD_DELAY(); LCD_WR_H(); LCD_DELAY(); } } /** *写命令 */ static void lcd_writeCmd(LcdStr* ps, u16 cmd) { LCD_CS_SEL(); lcd_sendBeData(ps, LCD_FLAG_CMD, 3); //100 lcd_sendBeData(ps, cmd, 9); LCD_CS_RELAESE(); LCD_DELAY(); }
复制代码初始化
static void lcd_init(LcdStr* ps) { ...//MCU的GPIO初始化 LCD_CS_RELAESE();//片选脚拉高 LCD_WR_H(); //读写控制拉高 LCD_DELAY(); //--------------- lcd_writeCmd(ps, LCD_CMD_BIAS_COM | LCD_USE_COM4 | LCD_BIAS_1P3);//1/3偏压 4公共口 lcd_writeCmd(ps, LCD_RC256); //内部RC振荡 lcd_writeCmd(ps, LCD_CMD_SYS_DIS); //关系统振荡器和LCD偏压发生器 lcd_writeCmd(ps, LCD_WDTDIS1); lcd_writeCmd(ps, LCD_CMD_SYS_EN); //打开系统振荡器 lcd_writeCmd(ps, LCD_CMD_Normal); lcd_writeCmd(ps, LCD_CMD_ON); //开LCD偏压 lcd_clearAll(ps); //清除屏幕数据,就是全部写0}
显示
/** * 显示所有 */ static void lcd_showAll(LcdStr* ps) { LCD_CS_SEL(); lcd_sendBeData(ps, LCD_FLAG_DATA, 3); //标识101 lcd_sendBeData(ps, ps->startSeg, 6); //地址 for (int s = 0; s < 4; s++) { lcd_sendLeData(ps, ps->lcds >> (s * 8), 8); } LCD_CS_RELAESE(); LCD_DELAY(); }
复制代码清除
/** *清除屏幕 */ static void lcd_clearAll(LcdStr* ps) { LCD_CS_SEL(); lcd_sendBeData(ps, LCD_FLAG_DATA, 3); lcd_sendBeData(ps, 0, 6); //地址 for (int s = 0; s < 16; s++) { lcd_sendLeData(ps, 0, 8); } LCD_CS_RELAESE(); LCD_DELAY(); }
复制代码