2. 硬件连接与初始化:LCD引脚定义、电源与背光电路、初始化时序、复位序列

好,咱们进入正题。上一章我们把LCD的选型聊完了,这一章要动真格的了——把屏幕焊上去,让它亮起来。

说实话,硬件连接这块,我见过太多人栽跟头。明明代码写得没问题,屏幕就是不亮。最后拿万用表一量,哦,背光没供电。或者复位引脚悬空了。嗯,这些坑我都踩过,今天咱们一个一个填上。

2.1 LCD引脚定义:别被密密麻麻的引脚吓到

你拿到一块LCD模块,翻到背面,看到一排引脚——少则16个,多则40个。别慌。其实真正要你操心的,就那么几个。

我以最常用的128×64点阵屏为例,它通常是20个引脚。咱们挑关键的讲:

引脚编号 符号 功能说明 我给你的建议
1 VSS 电源地(GND) 必须接,别偷懒
2 VDD 电源正(3.3V或5V) 看数据手册,别猜
3 VO 对比度调节 接电位器到VDD,调到你看着舒服
4 RS 数据/指令选择 高电平=数据,低电平=指令
5 R/W 读/写选择 我们一般只写,直接接地
6 E 使能信号 下降沿锁存数据,关键信号
7~14 DB0~DB7 8位数据总线 4位模式只用高4位
15 LED+ 背光正极 串电阻限流,别直连
16 LED- 背光负极 接地

我个人习惯,把RS、E、DB4~DB7这四个信号接到MCU的连续GPIO上,方便后面用位操作。你想想看,如果引脚分布得乱七八糟,写代码时移位操作能把你逼疯。

小技巧: 如果你用的是4位模式(省引脚),DB0~DB3可以悬空。但别把DB4~DB7接反了,我见过有人把DB4接到DB7的位置,结果显示全乱码,查了一下午。

2.2 电源与背光电路:供电不稳,一切白搭

LCD模块的电源,说白了就两路:一路给逻辑电路,一路给背光。

逻辑电源: 大部分模块支持3.3V或5V。但注意,有些老模块只认5V。我建议你养成好习惯——先看数据手册的“Supply Voltage”一栏。我曾经在一个项目里,直接把3.3V接到一个5V模块上,结果屏幕灰蒙蒙的,字都看不清。后来加了电平转换才搞定。

背光电路: 这里有个坑。背光LED的典型电流是20mA~80mA,但很多模块的背光引脚没有内置限流电阻。你要是直接接3.3V,电流可能飙到100mA以上,轻则屏幕发烫,重则烧掉背光。

正确的做法是串一个电阻。阻值怎么算?很简单:

R = (VCC - V_LED) / I_LED

举个例子:
VCC = 3.3V,V_LED ≈ 3.0V(白光LED典型值)
I_LED = 40mA(取中间值)
R = (3.3 - 3.0) / 0.04 = 7.5Ω

实际取标称值10Ω,电流约30mA,够亮了。
警告: 别为了省事把背光直接接到MCU的GPIO上!GPIO的驱动能力通常只有几毫安,带不动背光。要用三极管或MOS管做开关。我早期做项目时就这么干过,结果GPIO烧了,MCU也跟着报废。

如果你想让MCU控制背光开关(比如血糖仪在待机时关掉背光省电),可以用一个NPN三极管:

// 伪代码示意
#define BACKLIGHT_PIN  PB0

void backlight_on() {
    set_gpio_high(BACKLIGHT_PIN);  // 三极管导通,背光亮
}

void backlight_off() {
    set_gpio_low(BACKLIGHT_PIN);   // 三极管截止,背光灭
}

2.3 初始化时序:别急着发数据,先让屏幕醒过来

LCD模块上电后,不会马上准备好接收指令。它内部有个复位过程,需要一点时间。这个时间,数据手册上叫“Power-on Reset Time”,一般是10ms~100ms。

我见过有人上电后立刻发指令,结果屏幕没反应。为什么?因为模块还在“睡懒觉”。正确的初始化流程应该是:

  1. 上电——给VDD和VSS供电
  2. 等待——延时至少40ms(保守点给100ms)
  3. 发复位指令——0x30(8位模式)或0x20(4位模式)
  4. 再等待——延时4.5ms以上
  5. 发功能设置——告诉屏幕用几线、几行、什么字体
  6. 发显示开关——先关掉显示,配置好再打开
  7. 清屏——把显存里的垃圾数据清掉
  8. 开显示——终于可以显示内容了

这里我贴一段实际项目里用过的初始化代码,用的是4位模式:

void LCD_Init(void) {
    // 1. 上电后等待
    delay_ms(50);

    // 2. 复位序列(4位模式专用)
    // 先发三次0x30,让屏幕进入8位模式
    LCD_WriteCmd_4bit(0x30);
    delay_ms(5);
    LCD_WriteCmd_4bit(0x30);
    delay_ms(5);
    LCD_WriteCmd_4bit(0x30);
    delay_ms(5);

    // 3. 切换到4位模式
    LCD_WriteCmd_4bit(0x20);
    delay_ms(5);

    // 4. 功能设置:4位模式,2行,5x7点阵
    LCD_WriteCmd(0x28);
    delay_ms(1);

    // 5. 显示开关:关显示
    LCD_WriteCmd(0x08);
    delay_ms(1);

    // 6. 清屏
    LCD_WriteCmd(0x01);
    delay_ms(2);

    // 7. 输入模式:光标右移,不移位
    LCD_WriteCmd(0x06);
    delay_ms(1);

    // 8. 开显示,关光标
    LCD_WriteCmd(0x0C);
    delay_ms(1);
}
关键点: 第2步的复位序列,很多人会漏掉。如果你用的是4位模式,必须先让屏幕进入8位模式,再切回4位。为什么?因为上电后屏幕默认是8位模式,你直接发4位指令它听不懂。这个坑,我当年调了整整一个晚上才想明白。

2.4 复位序列:硬件复位 vs 软件复位

LCD模块通常有两种复位方式:

  • 硬件复位: 通过RST引脚拉低再拉高。简单粗暴,但需要多占用一个GPIO。
  • 软件复位: 通过发指令序列来复位。省引脚,但时序要求严格。

我个人更倾向于软件复位,因为省引脚。在血糖仪这种小设备上,GPIO是稀缺资源,能省一个是一个。

但如果你发现屏幕初始化后显示异常(比如花屏、乱码),可以试试硬件复位。我曾经在一个项目中,屏幕偶尔上电后显示错位,加了硬件复位后问题就消失了。说白了,硬件复位更可靠,但软件复位更方便。

硬件复位的典型时序是这样的:

void LCD_HardReset(void) {
    // 拉低RST引脚
    set_gpio_low(RST_PIN);
    delay_ms(10);   // 保持低电平至少10ms

    // 拉高RST引脚
    set_gpio_high(RST_PIN);
    delay_ms(50);   // 等待内部复位完成
}
避坑指南: 我曾经在批量生产时发现,同一批模块,有的上电就能正常工作,有的需要两次复位。后来查资料才知道,不同批次的LCD模块,内部复位电路的电容容值有偏差,导致复位时间不一致。解决方案很简单——把复位后的等待时间从50ms加到100ms。从此再没出过问题。

小结

这一章的内容,说白了就是三件事:

  • 引脚连接: 别接错,尤其是电源和背光
  • 电源电路: 背光要串电阻,别直连
  • 初始化时序: 上电后等一等,复位序列别省

下一章,咱们要开始写驱动函数了——往屏幕上写一个字符,让它真正显示出来。到时候你会发现,前面这些硬件工作做得越扎实,后面写代码就越顺手。

嗯,今天就到这儿。有问题欢迎在评论区留言,我看到会回复。