Что означает print(char&)?
- Войдите на сайт для отправки комментариев
Вс, 06/12/2020 - 23:45
Пытаюсь вывести на экран lcd1602 массив символов типа char, используя библиотеку https://github.com/ssilver2007/LCD_1602_RUS_ALL
Компилятор ругается на строчку
lcd.print(arr[i]);
Код целиком:
#define _LCD_TYPE 2 // тип подключения дисплея
#include <font_LCD_1602_RUS.h>
#include <LCD_1602_RUS_ALL.h>
LCD_1602_RUS <LiquidCrystal> lcd(12, 11, 5, 4, 3, 2);
char arr[]= "Проверка вывода!"; // массив символов
void setup() {
Serial.begin(9600);
lcd.begin(16, 2);
}
void loop() {
lcd.setCursor(0, 0);
for (int i = 0; i < ((sizeof(arr)/sizeof(char)) - 1); i++)
{
lcd.print(arr[i]); // вывести символ массива
// lcd.print(*(arr+i)); // так тоже пробовал
delay(1000);
}
lcd.clear();
}Сообщение компилятора:
no matching function for call to 'LCD_1602_RUS<LiquidCrystal>::print(char&)
Он не может найти в библиотеке функцию с "char&"? А откуда возле char взялась эта закорючка? Объясните пожалуйста, кто разбирается!
через String попробуйте
Попробовал вот так, используя String, а не char:
#define _LCD_TYPE 2 // тип подключения дисплея #include <font_LCD_1602_RUS.h> #include <LCD_1602_RUS_ALL.h> LCD_1602_RUS <LiquidCrystal> lcd(12, 11, 5, 4, 3, 2); String stroka = "Проверка вывода!"; void setup() { Serial.begin(9600); lcd.begin(16, 2); } void loop() { lcd.setCursor(0, 0); for (int i = 0; i < ((sizeof(stroka)/sizeof(String)) - 1); i++) { lcd.print(stroka[i]); // вывести символ массива // lcd.print(*(arr+i)); // так тоже пробовал delay(1000); } lcd.clear(); }Всё равно компилятор пишет:
в строку 17 выводить переменную собрав её в String
#define _LCD_TYPE 2 // тип подключения дисплея //#include <font_LCD_1602_RUS.h> //#include <LCD_1602_RUS_ALL.h> // LCD_1602_RUS <LiquidCrystal> lcd(12, 11, 5, 4, 3, 2); #include <LCD_1602_RUS.h> LCD_1602_RUS lcd(0x27, 16, 2); char arr[]= "Проверка вывода!"; // массив символов String mysimvol; void setup() { Serial.begin(9600); lcd.begin(); } void loop() { lcd.setCursor(0, 0); for (int i = 0; i < ((sizeof(arr)/sizeof(char)) - 1); i++) { mysimvol = String(arr[i]); lcd.print(mysimvol); // вывести символ массива // lcd.print(*(arr+i)); // так тоже пробовал delay(1000); } lcd.clear(); }Большое спасибо за подсказку! Компилятор перестал ругаться, однако русские буквы не отображаются - вместо них какие-то символы!
Нормальный вывод получается только с массивом такого типа:
char *arr[] = {"Т", "е", "с", "т", " ", "д", "и", "с", "п", "л", "е", "я", "!"};Если я не ошибаюсь, это массив указателей! Интересно можно ли обойтись без него? А может быть есть какая-то функция для преобразования в такой массив обычной строки? Подскажите пожалуйста!
Чем не устраивает:
char arr[]=" Hello World";
?
Откройте пример SerialToLCD_I2C.ino и посмотрите на строки №№41 и 51. А потом делайте также со своим char.
Спасибо за подсказку! Попробовал, следуя Вашей рекомендации, использовать готовую библиотечную функцию
Получилось вот так
#define _LCD_TYPE 2 #include <font_LCD_1602_RUS.h> #include <LCD_1602_RUS_ALL.h> LCD_1602_RUS <LiquidCrystal> lcd(12, 11, 5, 4, 3, 2); char str[] = "Test! Проверка вывода!"; void setup() { Serial.begin(9600); lcd.begin(16, 2); } void loop() { unsigned char w_str[2]; // char w_str[]; lcd.setCursor(0, 0); for (int i = 0; i < (sizeof(str) / sizeof(str[0])); i++) { w_str[0] = str[i]; if (w_str[0] > 0x7F) { w_str[1] = str[i + 1]; //Если кириллица, то читаем второй байт } lcd.print(lcd.ascii_utf8(w_str));//Вывод на экран LCD, в т.ч. по-русски. Перевод из ASCII в UTF-8. delay(1000); } lcd.clear(); }Но дело в том в том, что символы кириллицы почему-то выводятся два раза подряд!
Например слово "Привет" выводится так "ППррииввеетт", а вот "Hello" - нормально!
Подозреваю, что ошибка может быть в этой стоке
Я написал там i+1, так как думаю, что для перехода к следующему байту нужно добавить единицу!
Нет, ошибка не в этой строке, ошибка - в алгоритме. Вы печатаете столько символов, сколько байт в исходной строке. Но некоторые символы занимают два байта, поэтому и печатать нужно не на каждом байте.
Хотя, в принципе, можно поправить и именно эту строку: str[++i]; - не проверял, но смысл в том, чтобы, встретив символ кириллицы, инкрементировать цикл не на 1, а на 2.
Да! Вы абсолютно правы! Это работает!
#define _LCD_TYPE 2 #include <font_LCD_1602_RUS.h> #include <LCD_1602_RUS_ALL.h> LCD_1602_RUS <LiquidCrystal> lcd(12, 11, 5, 4, 3, 2); char str[] = "Test! Проверка вывода!"; void setup() { Serial.begin(9600); lcd.begin(16, 2); } void loop() { unsigned char w_str[2]; lcd.setCursor(0, 0); for (int i = 0; i < (sizeof(str) / sizeof(str[0])); i++) { w_str[0] = str[i]; if (w_str[0] > 0x7F) { w_str[1] = str[++i ]; // вначале увеличиваем индекс, чтобы считать второй байт } lcd.print(lcd.ascii_utf8(w_str));//Вывод на экран LCD, в т.ч. по-русски. Перевод из ASCII в UTF-8. delay(200); } lcd.clear(); }Вот так тоже работает:
if (w_str[0] > 0x7F) { //Если кириллица, то... i++; // изменить индекс для перехода w_str[1] = str[i]; // считать второй байт }Большое спасибо Вам за подсказку!
Добавил в текст программы ещё автоматический перенос на следующую строку, правда для этого пришлось ввести ещё одну переменную! Чтобы подсчитывались выведенные символы!
#include <LCD_1602_RUS_ALL.h> LCD_1602_RUS <LiquidCrystal> lcd(12, 11, 5, 4, 3, 2); const int displayTime = 1000; const int symbolTime = 300; char str[] = "abc абв abc абв!"; void setup() { Serial.begin(9600); lcd.begin(16, 2); } void loop() { unsigned char w_str[2]; lcd.setCursor(0, 0); for (int i = 0, symbolCount = 0; i < (sizeof(str) / sizeof(str[0])); i++) //symbolCount для подсчета выведенных символов { //Serial.println(symbolCount); //Serial.println(c); w_str[0] = str[i]; if (w_str[0] > 0x7F) { i++; // вначале увеличиваем индекс, чтобы считать второй байт w_str[1] = str[i]; } lcd.print(lcd.ascii_utf8(w_str));//Вывод на экран LCD, в т.ч. по-русски. Перевод из ASCII в UTF-8. symbolCount++; delay(symbolTime); //* if ((symbolCount % 16) == 0) { lcd.setCursor(0, 1); } if ((symbolCount) % 32 == 0) { delay(displayTime); lcd.clear(); lcd.setCursor(0, 0); } //*/ } delay(displayTime); lcd.clear(); }Всё вроде бы работает нормально. Но вот всё-таки интересно, можно ли было обойтись без этой переменной? Кто разбирается, подскажите пожалуйста!
вапще, 1602 может содержать 40 символов в 1 строке. Можно выводить всё в одну строку и делать горизонтальный скролл влево и вправо.
Почитай, мошт поймёшь чо
https://xn--18-6kcdusowgbt1a4b.xn--p1ai/lcd-1602-%D0%B1%D0%B5%D0%B3%D1%83%D1%89%D0%B0%D1%8F-%D1%81%D1%82%D1%80%D0%BE%D0%BA%D0%B0/