【问题标题】:Protocol for writing data to 16x2 LCD via I2C通过 I2C 将数据写入 16x2 LCD 的协议
【发布时间】:2017-06-29 23:32:40
【问题描述】:

我是电子新手,已经完成了有关如何使用liquidCrystal_I2C 在 Arduino 中通过 I2C 操作 16x2 字符 LCD 的教程。一切正常,但我对 I2C 和 LCD 之间的低级交互有疑问。查看库的源代码,我注意到在编写 4 位半字节 (LiquidCrystal_I2C::write4bits) 时,代码首先将半字节写入 I2C 扩展器 (LiquidCrystal_I2C::expanderWrite),然后在触发 Enable 位时写入再次。为什么第一个expanderWrite 是必要的?为什么 write4bits 不能只调用pulseEnable(设置了黑光位)?

我确信这是有原因的,因为我检查了 RPCLCD 等其他库并看到了类似的模式。任何人都可以启发我吗?谢谢。

【问题讨论】:

    标签: arduino i2c


    【解决方案1】:

    datasheet我发现LCD在通信协议中需要特定的时序。 在使能线的上升沿,寄存器选择和读/写线必须已经稳定为 tsu1 (100ns)。在使能线的下降沿,数据必须已经稳定到 tsu2 (60ns)。通过写_data,他们也写了RS和R/W行,因为它们是_data的低半字节。

    This article 非常彻底地涵盖了该主题。

    //**** From LiquidCrystal_I2C.h
    // flags for backlight control
    #define LCD_BACKLIGHT 0x08
    #define LCD_NOBACKLIGHT 0x00
    
    #define En B00000100  // Enable bit
    #define Rw B00000010  // Read/Write bit
    #define Rs B00000001  // Register select bit
    //              ^--------Backlight bit defined above
    //          ^^^^---------Data bits
    
    //**** From LiquidCrystal_I2C.cpp
    void LiquidCrystal_I2C::write4bits(uint8_t value) {
        expanderWrite(value);
        pulseEnable(value);
    }
    
    void LiquidCrystal_I2C::expanderWrite(uint8_t _data){
        Wire.beginTransmission(_addr);
        Wire.write((int)(_data) | _backlightval);
        Wire.endTransmission();
    }
    
    void LiquidCrystal_I2C::pulseEnable(uint8_t _data){
        expanderWrite(_data | En);  // En high
        delayMicroseconds(1);       // enable pulse must be >450ns
    
        expanderWrite(_data & ~En); // En low
        delayMicroseconds(50);      // commands need > 37us to settle
    }
    

    【讨论】:

    • 谢谢!我想这就是原因!
    猜你喜欢
    • 1970-01-01
    • 2021-12-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多