You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

PIC16F88搭配HD44780型16x2 LCD无显示问题排查求助

PIC16F88 + HD44780 LCD无显示问题排查

问题描述

我正在开发基于PIC16F88单片机的项目,采用4位模式连接HD44780兼容的16x2 LCD,使用MikroC PRO for PIC编写程序。无论仿真还是实际电路运行,LCD完全无显示,甚至没有黑色方块。

已完成的检查

  • 程序开头调用了Lcd_Init();
  • 使用Lcd_Out()时坐标和字符串参数正确;
  • 单片机与LCD的RS、EN、D4-D7引脚连接无误;
  • 已通过10k电位器正确调节LCD对比度引脚VEE;
  • 电源稳定,RW和VSS引脚已接地;
  • PIC16F88配置位设置正确(如INTOSC、按需禁用MCLR等)。

完整代码

sbit LCD_RS at RB4_bit;
sbit LCD_EN at RB5_bit;
sbit LCD_D4 at RB0_bit;
sbit LCD_D5 at RB1_bit;
sbit LCD_D6 at RB2_bit;
sbit LCD_D7 at RB3_bit;

sbit LCD_RS_Direction at TRISB4_bit;
sbit LCD_EN_Direction at TRISB5_bit;
sbit LCD_D4_Direction at TRISB0_bit;
sbit LCD_D5_Direction at TRISB1_bit;
sbit LCD_D6_Direction at TRISB2_bit;
sbit LCD_D7_Direction at TRISB3_bit;

unsigned int voltage = 0;
unsigned int delay_time = 5;
unsigned int high_threshold = 255;
unsigned int low_threshold = 110;
unsigned int stage1 = 140;
unsigned int stage2 = 160;
unsigned int stage3 = 180;
unsigned int stage4 = 200;

unsigned int hysteresis = 5;

unsigned short relay_state = 0x00;

void EEPROM_Write_Settings() {
  EEPROM_Write(0x00, high_threshold);
  EEPROM_Write(0x01, low_threshold);
  EEPROM_Write(0x02, delay_time);
}

void EEPROM_Read_Settings() {
  high_threshold = EEPROM_Read(0x00);
  low_threshold = EEPROM_Read(0x01);
  delay_time = EEPROM_Read(0x02);

  if (high_threshold > 250 || high_threshold < 180) high_threshold = 255;
  if (low_threshold < 90 || low_threshold > 200) low_threshold = 110;
  if (delay_time == 0 || delay_time > 10) delay_time = 5;
}

void flexible_delay(unsigned int seconds) {
  unsigned int i;
  for(i = 0; i < seconds * 10; i++) {
    Delay_ms(100);
  }
}

unsigned int read_voltage() {
  unsigned int adc = ADC_Read(0);
  return (adc * 5.0 * 100.0) / 1023.0;
}

void init() {
  TRISA = 0xFF;
  TRISB = 0x00;
  ADC_Init();
  Lcd_Init();
  Lcd_Cmd(_LCD_CLEAR);
  Lcd_Cmd(_LCD_CURSOR_OFF);
  EEPROM_Read_Settings();
}

void show_voltage(unsigned int v) {
  char txt[16];
  Lcd_Cmd(_LCD_CLEAR);
  Lcd_Out(1,1,"Voltage:");
  IntToStr(v, txt);
  Lcd_Out(2,1,txt);
  Lcd_Out(2,7,"V");
}

void control_relays(unsigned int v) {
  if(v < low_threshold - hysteresis || v > high_threshold + hysteresis) {
    PORTB &= 0xF0;
    relay_state = 0;
    return;
  }

  if(v >= stage4) relay_state = 0x0F;
  else if(v >= stage3) relay_state = 0x07;
  else if(v >= stage2) relay_state = 0x03;
  else if(v >= stage1) relay_state = 0x01;
  else relay_state = 0x00;

  PORTB = (PORTB & 0xF0) | relay_state;
}

void check_buttons() {
  if (Button(&PORTA, 1, 50, 1)) {
    high_threshold += 5;
    if (high_threshold > 255) high_threshold = 200;
    EEPROM_Write_Settings();
  }

  if (Button(&PORTA, 2, 50, 1)) {
    low_threshold -= 5;
    if (low_threshold < 100) low_threshold = 180;
    EEPROM_Write_Settings();
  }

  if (Button(&PORTA, 3, 50, 1)) {
    delay_time++;
    if (delay_time > 10) delay_time = 1;
    EEPROM_Write_Settings();
  }
}

void main() {
  init();
  while(1) {
    voltage = read_voltage();
    show_voltage(voltage);
    control_relays(voltage);
    check_buttons();
    flexible_delay(delay_time);
  }
}

排查建议

  1. RB端口冲突排查:代码中TRISB = 0x00将整个B口设为输出,但control_relays函数会修改PORTB低4位(与LCD数据线D4-D7复用)。先注释掉control_relays和check_buttons的调用,仅保留LCD初始化与显示逻辑,测试LCD是否能正常工作。
  2. 时钟配置匹配检查:确认MikroC项目设置中的时钟频率与PIC16F88配置位的INTOSC频率一致(如8MHz或4MHz),错误的时钟会导致LCD初始化时序失效。
  3. 引脚方向优先级验证:在Lcd_Init()后检查TRISB寄存器状态,或把LCD引脚方向配置放在TRISB = 0x00之后,确保LCD相关引脚方向被正确设为输出。
  4. 初始化顺序调整:尝试交换ADC_Init()与Lcd_Init()的顺序,先初始化LCD再初始化ADC,避免ADC模块对RB端口的潜在干扰。
  5. 电源电平再确认:确保LCD的VCC与PIC同为5V,若使用3.3V LCD需添加电平转换电路。重新调节VEE电位器,部分LCD需要VEE接负电压才能显示,可尝试将电位器一端接地、一端接VCC,缓慢调节中间抽头。

内容的提问来源于stack exchange,提问作者ahmed hasan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.12 19:34:58