STM32-LCD-HD44780-I2C
STM32-LCD-HD44780-I2C copied to clipboard
double strobe
Зачем вы дважды посылаете один и тот же набор данных? Ваш код
static bool lcdWriteByte(uint8_t rsRwBits, uint8_t * data) {
/* Higher 4 bits*/
lcdCommandBuffer[0] = rsRwBits | LCD_BIT_E | lcdParams.backlight | (*data & 0xF0); // Send data and set strobe
lcdCommandBuffer[1] = lcdCommandBuffer[0]; // Strobe turned on
lcdCommandBuffer[2] = rsRwBits | lcdParams.backlight | (*data & 0xF0); // Turning strobe off
/* Lower 4 bits*/
lcdCommandBuffer[3] = rsRwBits | LCD_BIT_E | lcdParams.backlight | ((*data << 4) & 0xF0); // Send data and set strobe
lcdCommandBuffer[4] = lcdCommandBuffer[3]; // Strobe turned on
lcdCommandBuffer[5] = rsRwBits | lcdParams.backlight | ((*data << 4) & 0xF0); // Turning strobe off
if (HAL_I2C_Master_Transmit_DMA(lcdParams.hi2c, lcdParams.address, (uint8_t*)lcdCommandBuffer, 6) != HAL_OK) {
return false;
}
while (HAL_I2C_GetState(lcdParams.hi2c) != HAL_I2C_STATE_READY) {
vTaskDelay(1);
}
return true;
}
Изменил на такой. Работает отлично на FDCC2004D-FLYYBW-51LR.
static bool lcdWriteByte(uint8_t rsRwBits, uint8_t * data) {
/* Higher 4 bits*/
lcdCommandBuffer[0] = rsRwBits | LCD_BIT_E | lcdParams.backlight | (*data & 0xF0); // Send data and set strobe
//lcdCommandBuffer[1] = lcdCommandBuffer[0]; // Strobe turned on
lcdCommandBuffer[1] = rsRwBits | lcdParams.backlight | (*data & 0xF0); // Turning strobe off
/* Lower 4 bits*/
lcdCommandBuffer[2] = rsRwBits | LCD_BIT_E | lcdParams.backlight | ((*data << 4) & 0xF0); // Send data and set strobe
//lcdCommandBuffer[4] = lcdCommandBuffer[3]; // Strobe turned on
lcdCommandBuffer[3] = rsRwBits | lcdParams.backlight | ((*data << 4) & 0xF0); // Turning strobe off
if (HAL_I2C_Master_Transmit_DMA(lcdParams.hi2c, lcdParams.address, (uint8_t*)lcdCommandBuffer, 4) != HAL_OK) {
return false;
}
while (HAL_I2C_GetState(lcdParams.hi2c) != HAL_I2C_STATE_READY) {
vTaskDelay(1);
}
return true;
}
Добрый день!
Это хак для алишных дисплеев, я описал его тут http://blog.bulki.me/stm32/hal/arduino/lcd/2017/12/20/Create-lib-for-stm32-LCD.html
Для того, чтобы выдавать строб, мы дважды шлём первую партию 4-х бит. Третьим байтом шлём младшие 4-бит и закрываем строб.
При таком раскладе и скорости шины I2C в 100кбит, ширина строба ~180мкс, пауза между стробами ~90мкс, и пауза между парными стробами ~530мкс. По идее, и я так думал предварительно, можно не удлинять строб на два байта, обойтись одним. Но на деле оказалось, что 90мкс мало для ширины строба, но достаточно для паузы между стробами. Похоже, что кварц в дисплее работает на более низкой частоте, чем положено по даташиту.
чт, 7 янв. 2021 г., 05:49 AndreiCherniaev [email protected]:
Зачем вы дважды посылаете один и тот же набор данных? Ваш код
static bool lcdWriteByte(uint8_t rsRwBits, uint8_t * data) {
/* Higher 4 bits*/ lcdCommandBuffer[0] = rsRwBits | LCD_BIT_E | lcdParams.backlight | (*data & 0xF0); // Send data and set strobe lcdCommandBuffer[1] = lcdCommandBuffer[0]; // Strobe turned on lcdCommandBuffer[2] = rsRwBits | lcdParams.backlight | (*data & 0xF0); // Turning strobe off /* Lower 4 bits*/ lcdCommandBuffer[3] = rsRwBits | LCD_BIT_E | lcdParams.backlight | ((*data << 4) & 0xF0); // Send data and set strobe lcdCommandBuffer[4] = lcdCommandBuffer[3]; // Strobe turned on lcdCommandBuffer[5] = rsRwBits | lcdParams.backlight | ((*data << 4) & 0xF0); // Turning strobe off if (HAL_I2C_Master_Transmit_DMA(lcdParams.hi2c, lcdParams.address, (uint8_t*)lcdCommandBuffer, 6) != HAL_OK) { return false; } while (HAL_I2C_GetState(lcdParams.hi2c) != HAL_I2C_STATE_READY) { vTaskDelay(1); } return true;}
Изменил на такой. Работает отлично на FDCC2004D-FLYYBW-51LR.
static bool lcdWriteByte(uint8_t rsRwBits, uint8_t * data) {
/* Higher 4 bits*/ lcdCommandBuffer[0] = rsRwBits | LCD_BIT_E | lcdParams.backlight | (*data & 0xF0); // Send data and set strobe //lcdCommandBuffer[1] = lcdCommandBuffer[0]; // Strobe turned on lcdCommandBuffer[1] = rsRwBits | lcdParams.backlight | (*data & 0xF0); // Turning strobe off /* Lower 4 bits*/ lcdCommandBuffer[2] = rsRwBits | LCD_BIT_E | lcdParams.backlight | ((*data << 4) & 0xF0); // Send data and set strobe //lcdCommandBuffer[4] = lcdCommandBuffer[3]; // Strobe turned on lcdCommandBuffer[3] = rsRwBits | lcdParams.backlight | ((*data << 4) & 0xF0); // Turning strobe off if (HAL_I2C_Master_Transmit_DMA(lcdParams.hi2c, lcdParams.address, (uint8_t*)lcdCommandBuffer, 4) != HAL_OK) { return false; } while (HAL_I2C_GetState(lcdParams.hi2c) != HAL_I2C_STATE_READY) { vTaskDelay(1); } return true;}
— You are receiving this because you are subscribed to this thread. Reply to this email directly, view it on GitHub https://github.com/firebull/STM32-LCD-HD44780-I2C/issues/4, or unsubscribe https://github.com/notifications/unsubscribe-auth/AAC2IRWUHCTOQEE46ML6DKTSYUOLTANCNFSM4VYLQFZA .
Добрый день! Это хак для алишных дисплеев, я описал его тут http://blog.bulki.me/stm32/hal/arduino/lcd/2017/12/20/Create-lib-for-stm32-LCD.html Для того, чтобы выдавать строб, мы дважды шлём первую партию 4-х бит. Третьим байтом шлём младшие 4-бит и закрываем строб. При таком раскладе и скорости шины I2C в 100кбит, ширина строба ~180мкс, пауза между стробами ~90мкс, и пауза между парными стробами ~530мкс. По идее, и я так думал предварительно, можно не удлинять строб на два байта, обойтись одним. Но на деле оказалось, что 90мкс мало для ширины строба, но достаточно для паузы между стробами. Похоже, что кварц в дисплее работает на более низкой частоте, чем положено по даташиту. чт, 7 янв. 2021 г., 05:49 AndreiCherniaev [email protected]: … Зачем вы дважды посылаете один и тот же набор данных? Ваш код static bool lcdWriteByte(uint8_t rsRwBits, uint8_t * data) { /* Higher 4 bits*/ lcdCommandBuffer[0] = rsRwBits | LCD_BIT_E | lcdParams.backlight | (data & 0xF0); // Send data and set strobe lcdCommandBuffer[1] = lcdCommandBuffer[0]; // Strobe turned on lcdCommandBuffer[2] = rsRwBits | lcdParams.backlight | (data & 0xF0); // Turning strobe off / Lower 4 bits/ lcdCommandBuffer[3] = rsRwBits | LCD_BIT_E | lcdParams.backlight | ((data << 4) & 0xF0); // Send data and set strobe lcdCommandBuffer[4] = lcdCommandBuffer[3]; // Strobe turned on lcdCommandBuffer[5] = rsRwBits | lcdParams.backlight | ((data << 4) & 0xF0); // Turning strobe off if (HAL_I2C_Master_Transmit_DMA(lcdParams.hi2c, lcdParams.address, (uint8_t)lcdCommandBuffer, 6) != HAL_OK) { return false; } while (HAL_I2C_GetState(lcdParams.hi2c) != HAL_I2C_STATE_READY) { vTaskDelay(1); } return true; } Изменил на такой. Работает отлично на FDCC2004D-FLYYBW-51LR. static bool lcdWriteByte(uint8_t rsRwBits, uint8_t * data) { / Higher 4 bits*/ lcdCommandBuffer[0] = rsRwBits | LCD_BIT_E | lcdParams.backlight | (data & 0xF0); // Send data and set strobe //lcdCommandBuffer[1] = lcdCommandBuffer[0]; // Strobe turned on lcdCommandBuffer[1] = rsRwBits | lcdParams.backlight | (data & 0xF0); // Turning strobe off / Lower 4 bits/ lcdCommandBuffer[2] = rsRwBits | LCD_BIT_E | lcdParams.backlight | ((*data << 4) & 0xF0); // Send data and set strobe //lcdCommandBuffer[4] = lcdCommandBuffer[3]; // Strobe turned on lcdCommandBuffer[3] = rsRwBits | lcdParams.backlight | ((data << 4) & 0xF0); // Turning strobe off if (HAL_I2C_Master_Transmit_DMA(lcdParams.hi2c, lcdParams.address, (uint8_t)lcdCommandBuffer, 4) != HAL_OK) { return false; } while (HAL_I2C_GetState(lcdParams.hi2c) != HAL_I2C_STATE_READY) { vTaskDelay(1); } return true; } — You are receiving this because you are subscribed to this thread. Reply to this email directly, view it on GitHub <#4>, or unsubscribe https://github.com/notifications/unsubscribe-auth/AAC2IRWUHCTOQEE46ML6DKTSYUOLTANCNFSM4VYLQFZA .
Спасибо, интересное замечание.
Кстати в операции (*data << 4) & 0xF0 наложение маски лишнее.
Также хотел Вам заметить, что из моих соображений пользователь скорее всего будет выводить данные в lcd построчно и перед выводами строк будет значительная пауза. Таким образом имеет смысл модифицировать алгоритм. Сейчас:
- подготовка данных
- отправка
- ожидание конца отправки На такой а) ожидание конца отправки (скорее всего будет пролетать мгновенно) б) подготовка данных в) отправка