Вызовите Serial.print в отдельной вкладке / заголовочном файле

9

Я пишу программу на Arduino 0022.

Вызов Serial.printlnработает нормально в моем основном коде эскиза, но когда я пытаюсь использовать его в своем заголовочном файле " Menu.h", который находится на отдельной вкладке, я получаю ошибку:

В файле, включенном из AppController.cpp: 2:
Menu.h: в конструкторе «Menu :: Menu ()»:
Menu.h: 15: ошибка: «Serial» не был объявлен в этой области

Как я могу использовать Serial.printlnвне кода эскиза?

aaaidan
источник

Ответы:

3

Вы не должны вызывать функции из заголовочных файлов. Заголовочные файлы предназначены для определения макросов препроцессора (#define) и ссылок на переменные / функции в других файлах.

Вы должны создать несколько файлов C и связать их вместе во время компиляции. Заголовочный файл используется, чтобы сообщить каждому C-файлу, какие функции и переменные имеют другие C-файлы.

Чтобы использовать несколько файлов в Arduino IDE, вам необходим как минимум 1 заголовочный файл для описания функций, которые есть в других файлах, которыми вы хотите поделиться между ними. Кроме того, любые глобальные переменные, которые вы хотите использовать во всех файлах.

Эти определения должны быть дополнены атрибутом "external".

Затем вам нужно добавить один или несколько файлов "pde", которые содержат фактический код и определения переменных для функций.

Например, у меня есть файл "mouse.h":

extern void mouse_read(char *,char *, char *);
extern void mouse_init();

и файл "mouse.pde":

#include <ps2.h>

PS2 mouse(6,5);

void mouse_read(char *stat,char *x, char *y)
{
  mouse.write(0xeb);  // give me data!
  mouse.read();      // ignore ack
  *stat = mouse.read();
  *x = mouse.read();
  *y = mouse.read();
}

void mouse_init()
{
  mouse.write(0xff);  // reset
  mouse.read();  // ack byte
  mouse.read();  // blank */
  mouse.read();  // blank */
  mouse.write(0xf0);  // remote mode
  mouse.read();  // ack
  delayMicroseconds(100);
}

Тогда в моем основном файле у меня есть:

#include "mouse.h"

и я могу вызвать функции, которые находятся в «mouse.pde», как если бы они были в локальном файле.

Majenko
источник
Спасибо Majenko, ваш ответ очень полезен для меня, как для начинающего программиста C ++, и я обязательно приму ваш совет. Тем не менее, меня больше интересовало, почему класс Serial недоступен вне основного эскиза. Ура!
aaaidan
3

В качестве альтернативы очень хорошему ответу @ Majenko, вы можете создать класс C ++ для инкапсуляции ваших функций и поместить его в папку библиотек, как описано в http://www.arduino.cc/en/Hacking/LibraryTutorial .

Вам может понадобиться #include <Serial.h>в файле реализации вашего класса, чтобы иметь возможность вызывать последовательные методы. Я буду осторожен с этим, поскольку есть очевидные побочные эффекты при вызове последовательных функций (читайте, в частности). Я предпочитаю определять метод в моем классе, который принимает char * и передает байты из последовательного интерфейса в него из моей основной программы, а не взаимодействует напрямую с последовательным интерфейсом.


#if defined(ARDUINO) && ARDUINO >= 100
  #include "Arduino.h"
#else
  #include "WProgram.h"
#endif
vicatcu
источник
Привет! Да, я просмотрел в каталоге библиотеки arduino файл Serial.h или аналогичный, и все, что я смог найти, это HardwareSerial.h, в котором не было нужных мне определений. В конце я наткнулся на решение включить <WProgram.h>, который, кажется, объявляет объект Serial.
aaaidan
0

Я нашел способ Serialобъявить класс / объект в заголовочных файлах / вкладках:

#include <WProgram.h>  // at the top of the file

Это не кажется мне очень чистым, но, похоже, у него пока нет недостатков.

aaaidan
источник
1
Ах да, если вы хотите убедиться, что вы совместимы с Arduino 1.0, вы должны условно включить это или "Arduino.h" в зависимости от флага компиляции ARDUINO, подробности смотрите в моем ответе. Кроме того, ссылка на учебник в моем ответе говорит, что вы всегда должны включать WProgram.h в ваши классы
vicatcu