Странные строки


#include "Keypad.h"

char Incoming_value = 0;
String password = "123456";
String input = "";
const byte ROWS = 4; //four rows
const byte COLS = 4; //three columns
char keys[ROWS][COLS] = {
  {'1','2','3','A'},
  {'4','5','6','B'},
  {'7','8','9','C'},
  {'*','0','#','D'}
};

byte rowPins[ROWS] = {2, 3, 4, 5}; //connect to the row pinouts of the keypad
byte colPins[COLS] = {6,7,8,9}; //connect to the column pinouts of the keypad

Keypad keypad = Keypad( makeKeymap(keys), rowPins, colPins, ROWS, COLS );

void setup()
{
  Serial.begin(9600);
  pinMode(13, OUTPUT);
}

void loop()
{
  if (Serial.available() > 0)
  {
    Incoming_value = Serial.read();
    Serial.print(Incoming_value);
    Serial.print("enter value");
    if (Incoming_value == '1') {
      digitalWrite(13, HIGH);
      Serial.print("ON");
    }
    else if (Incoming_value == '0') {
      Serial.print("OFF");
      digitalWrite(13, LOW);
    }
  }
  // Read the pushed button
  char key = keypad.getKey();
  input = input + key;
  // just print the pressed key
  if (key) {
    Serial.println(key);
  }
  if(key == '*' ){
    Serial.println(input);
    if( input == password){
      digitalWrite(13, HIGH);
    }
  }
  if(key == '#'){
    digitalWrite(13, LOW);
    input = "";
  }
  
/*
  // this checkes if 4 is pressed, then do something. Here  we print the text but you can control something.
  if (key == '4') {
    Serial.println("Key 4 is pressed");
          digitalWrite(13, HIGH);
      Serial.print("ON");
  }
    if (key == '5') {
    Serial.println("Key 5 is pressed");
          digitalWrite(13, LOW);
      Serial.print("ON");
  }
  */
}

when print input variable i get strange text like

⸮⸮⸮⸮⸮⸮⸮;⸮⸮ߵ⸮⸮⸮⸮u⸮⸮⸮⸮⸮⸮?/}⸮⸮⸮⸮⸮⸮~⸮⸮⸮⸮⸮-d

what i can do ?

, 👍2

Обсуждение

Вероятно, вы не добавили задержку к концу " пустого цикла ()", @Sam Ruben Abraham

В качестве примера : загрузите JohnsProject/ArduOS с Github и запустите там основной скетч после ввода строки кода, которая вызывает реестр для запуска приложения "оболочка". Вы увидите, как произойдет та же самая странная вещь, @Sam Ruben Abraham

Кроме того, попробуйте добавить задержку, как я сказал в "void loop()" в вашем скетче, и посмотрите, сработает ли это., @Sam Ruben Abraham

Вы подтвердили, что скорость передачи данных вашего последовательного монитора IDE составляет 9600 (что и предполагается в вашем коде)?, @lurker

@lurker , мой ответ в порядке ? (Возможно, я могу добавить вашу точку зрения по настройке скорости передачи данных в бодах на последовательном мониторе, если хотите ;) ), @Sam Ruben Abraham


2 ответа


Лучший ответ:

3

Прежде всего, вы должны убедиться, что вы выбрали ту же скорость в последовательном мониторе, которую вы использовали в своем скетче с Serial.begin(). Эта ошибка очень распространена, и мусорные значения являются симптомом этого.

Но у вашего кода также есть проблемы. У вас есть входная переменная типа String, которая должна содержать пользовательский ввод для сравнения с паролем. Сразу после получения ключа вы добавляете этот ключ к строке. Вы предполагаете, что keypad.getKey() ждет, когда пользователь на самом деле нажмет клавишу, а затем вернет ее. Но это не так. keypad.getKey() вернет NO_KEY, когда пользователь в данный момент не нажимает клавишу. Это определяется в библиотеке клавиатуры как '\0' (нулевой символ), который отмечает конец строки. Ваш код работает очень быстро, поэтому вы добавляете все больше и больше нулевых символов в свою строку. Ваши строки становятся все больше и больше, заполняя вашу оперативную память очень быстро.

Как решить эту проблему: Вы должны использовать только возвращаемое значение keypad.getKey(), если клавиша была фактически нажата. Поместите весь код после него в оператор if, проверяя NO_KEY:

// Read the pushed button
char key = keypad.getKey();
if(key != NO_KEY){
    input = input + key;
    // just print the pressed key
    if (key) {
        Serial.println(key);
    }
    if(key == '*' ){
        Serial.println(input);
        if( input == password){
            digitalWrite(13, HIGH);
        }
    }
    if(key == '#'){
        digitalWrite(13, LOW);
        input = "";
    }
}
,

Хороший ответ ! Вы исправили код, который я не смог ! (+1), @Sam Ruben Abraham


1

PS: предложение @lurker в комментариях - проверьте также настройку скорости передачи данных в бодах на вашем последовательном мониторе.

ПРАВКА: Я признаю, что код в предыдущей версии этого ответа был глупо напечатан мной из-за недостатка терпения, так что я исправлю свою ошибку(не в коде, а в виде полного ответа).

Во-первых, я не понял, что вы хотите сделать с переменной Incoming_value в вашем скетче, поэтому я не буду говорить об этом; Я бы предложил добавить достаточно небольшую задержку в конце кода в цикле. Это должно дать последовательному порту некоторое время для обработки входящих данных и прекращения печати запутанного вывода (возможно , просто потому, что задержки заставляют ваш микроконтроллер ждать некоторое время, чтобы сделать что-то в другом месте, особенно там, где прием данных происходит медленно и таким образом избежать коллизий).

Также обратите внимание, что я не студент CS или фанат электроники, но я говорю на основе своих догадок. Любая поправка принимается.

,

Учитывая, что чаще всего задержки приносят больше вреда, чем пользы, в чем смысл их добавления сюда? Я понимаю, как они могли бы помочь в программе, которая отправляет данные очень медленному получателю, но здесь это не так. Чтобы код “работал гладко”, слишком расплывчато., @Edgar Bonet

@EdgarBonet извините за поздний ответ. Обратите внимание, что в том месте, где система настроена на получение нажатий клавиш, добавление задержки позволяет человеку вводить пароль (как в примере) ключом за ключом - и теперь это напоминает мне о том, как глупо я добавил код в свой ответ. Большое спасибо !! :D, @Sam Ruben Abraham