Как управлять светодиодом с сервера Thingspeak с помощью SIM900A и Arduino? - PullRequest
1 голос
/ 12 июня 2019

Я пытаюсь управлять светодиодом с сервера Thingspeak с помощью модуля GSM.Полученные данные успешно печатаются на последовательном мониторе (это «1» как последнее обновление), но когда я пытаюсь присвоить эти данные переменной, чтобы управлять встроенным светодиодом Arduino, ничего не происходит.

#include <SoftwareSerial.h>
SoftwareSerial SIM900A(10, 11);
void setup()
{
  pinMode(LED_BUILTIN, OUTPUT);
  SIM900A.begin(9600);
  Serial.begin(9600);
  while (!Serial)
    ;
  Serial.println("Arduino is ready");
  SIM900A.begin(9600);
  Serial.println("SIM900A started at 9600");
  delay(1000);
  Serial.println("Setup Complete");
}

void loop()
{
  SIM900A.println("AT");
  delay(1000);
  ShowSerialData();

  SIM900A.println("AT+CIPSHUT");
  delay(2000);
  ShowSerialData();

  SIM900A.println("AT+CIPMUX=0");
  delay(2000);
  ShowSerialData();

  SIM900A.println("AT+CGATT=1");
  delay(5000);

  SIM900A.println("AT+CSTT=\"INTERNET\",\"\",\"\"");
  delay(4000);

  SIM900A.println("AT+CIICR");
  delay(3000);
  ShowSerialData();

  SIM900A.println("AT+CIFSR");
  delay(5000);
  ShowSerialData();

  SIM900A.println("AT+CIPSTART=\"TCP\",\"184.106.153.149\",\"80\"");
  delay(4000);
  ShowSerialData();

  SIM900A.println("AT+CIPSEND");
  delay(4000);

  SIM900A.print("GET /channels/798173/fields/1/last");
  SIM900A.print("\r\n\x1A");
  ShowSerialData();

  char led = SIM900A.read();
  Serial.print(led);

  if (led == '1')
  {
    digitalWrite(LED_BUILTIN, HIGH);
  }

  else if (led == '0')
  {
    digitalWrite(LED_BUILTIN, LOW);
  }

  delay(8000);
}

void ShowSerialData()
{
  while (SIM900A.available() != 0)
    Serial.print(char(SIM900A.read()));
}

Последняя часть вывода с последовательного монитора:

CONNECT OK
AT+CIPSEND

> ⸮GET /channels/798173/fields/1/last

SEND OK
1

Ответы [ 3 ]

1 голос
/ 12 июня 2019

Как указывает @Saurabh P Bhandari, вы не можете читать одни и те же данные из последовательного порта дважды, поэтому вам нужно будет сначала прочитать данные в переменной, если вы хотите их использовать.

String getSerialData(){
      String buffer="";
      while (SIM900A.available() ){
        char c = SIM900A.read();
        buffer+=c;    
      }
      return buffer;
     }

Затем вы можете использовать String led = getSerialData() для заполнения led буфером.
Здесь вам нужно помнить, что функция getSerialData вернет что-либо, присутствующее в буфере, и будет выглядеть примерно так:

GET /channels/798173/fields/1/last
SEND

HTTP RESPONSE

Похоже, что вас интересует только HTTP RESPONSE, поэтому вы можете обновить свои условия так, чтобы они были

if(led.endsWith("1"))
...
else if(led.endsWith("0"))
1 голос
/ 12 июня 2019

Вероятно, вы ограничены в скорости, потому что слишком часто используете серверы ThingSpeak.Вы можете обновлять канал только один раз в 15 с бесплатной учетной записью.Очевидно, что нет смысла запрашивать значение быстрее, чем оно может быть обновлено, т. Е. Каждые 15 секунд с бесплатной учетной записью.

Подумайте о том, чтобы добавить в код некоторые необходимые задержки, чтобы ваше устройство не попало в черный список за злоупотребление условиями.

1 голос
/ 12 июня 2019

Из того, что я понял до сих пор, в этом фрагменте

SIM900A.print("GET /channels/798173/fields/1/last");  
SIM900A.print("\r\n\x1A");
ShowSerialData(); 

ShowSerialData() печатает вывод, который равен '1'.Затем вы немедленно читаете данные в переменную led.Поскольку фактические полученные данные печатаются уже с ShowSerialData(), при следующем вызове SIM900A.read() ничего не будет возвращено или следующий набор данных будет отправлен вашим модулем.

...