树莓派4驱动16x4 LCD时第3、4行字符显示右移异常
16x4 LCD 第三/四行显示固定偏移排查
问题根因
你遇到的4列固定位置偏移和硬件接线、供电无关(第一、二行显示正常可证明核心电路连接有效),本质是WiringPi驱动的LCD行地址映射和你使用的1604A模块的实际DDRAM地址不匹配。
HD44780架构的LCD模块地址存在两种常见的1604规格映射:
- 标准映射(多数模块):第三行起始地址
0x14、第四行起始地址0x54 - 简化映射(部分国产模块):第三行起始地址
0x10、第四行起始地址0x50
WiringPi在初始化4行LCD时,会根据传入的列数参数自动生成每行的起始偏移,计算逻辑为:
第0行偏移:
0x00
第1行偏移:0x40
第2行偏移:传入的列数参数
第3行偏移:传入的列数参数 +0x40
你当前代码中传入的列数参数为20,驱动计算出的第三行偏移为0x14、第四行偏移为0x54,刚好和采用简化映射的模块错位4个地址单位,对应你观察到的「x=1位置的内容实际显示在x=5位置」的4列偏移现象。
解决步骤
- 修改
lcdInit的列数参数为硬件实际值16
你当前传入20列的参数,和1604A模块实际16列的硬件规格不匹配,调整初始化代码:
此时驱动计算的第三行偏移为lcd = lcdInit(4, 16, 4, LCD_RS, LCD_E, LCD_D4, LCD_D5, LCD_D6, LCD_D7, 0, 0, 0, 0);0x10、第四行偏移为0x50,可直接匹配多数简化映射模块的地址,4列偏移会直接消除。 - 若修改后仍有偏移,手动校准行偏移值
WiringPi的LCD句柄对应可访问的设备结构体中,按行顺序存储了每行的DDRAM偏移,可在初始化完成后直接改写校准:// 初始化完成后插入校准代码 struct lcdDevice *lcd_dev = (struct lcdDevice *)lcd; // 根据实际硬件映射调整偏移值,可测试0x10/0x14两个值的显示效果 lcd_dev->rowOffsets[2] = 0x10; // 第三行实际起始地址 lcd_dev->rowOffsets[3] = 0x50; // 第四行实际起始地址 - 注意:初始化时不要传入超过硬件实际列宽的参数,否则WiringPi的文本自动滚动、行换行逻辑会出现异常。
快速验证方法
校准完成后,逐列输出标记验证位置正确性:
for (int col = 0; col < 16; col++) { lcdPosition(lcd, col, 2); lcdPuts(lcd, "*"); }
如果16个星号依次均匀显示在第三行的全部16个位置,说明偏移校准完成。
内容的提问来源于stack exchange,提问作者Sriyan Arosha
相关产品推荐
相关产品推荐

